正确使用avcodec_encode_video2()刷新

时间:2016-02-05 03:58:56

标签: video ffmpeg h.264 video-encoding

我有一个相机将图片发送到回调函数,我想使用FFmpeg制作带有这些图片的电影。我已按照decoding_encoding示例here进行操作,但不确定如何使用got_output来刷新编码器并获取延迟帧。

  1. Shoud我对所有相机的图片到达时进行编码,之后当我想停止拍摄并关闭视频时,我会进行冲洗循环吗?
  2. 或者

    1. 我是否应定期进行冲洗,让我们说每100张照片都会收到?
    2. 我的视频捕捉程序可能会运行几个小时,所以我担心这个延迟的帧如何在内存消耗中起作用,如果它们在那里堆叠直到刷新,这可能会占用我所有的记忆。

      这是示例执行的编码,它为1秒的视频制作了25个虚拟Frames,后来,它循环遍历avcodec_encode_video2()寻找got_output延迟帧:

      /////  Prepare the Frame, CodecContext and some aditional logic.....
      
      /* encode 1 second of video */
      for (i = 0; i < 25; i++) {
          av_init_packet(&pkt);
          pkt.data = NULL;    // packet data will be allocated by the encoder
          pkt.size = 0;
          fflush(stdout);
          /* prepare a dummy image */
          /* Y */
          for (y = 0; y < c->height; y++) {
              for (x = 0; x < c->width; x++) {
                  frame->data[0][y * frame->linesize[0] + x] = x + y + i * 3;
              }
          }
          /* Cb and Cr */
          for (y = 0; y < c->height/2; y++) {
              for (x = 0; x < c->width/2; x++) {
                  frame->data[1][y * frame->linesize[1] + x] = 128 + y + i * 2;
                  frame->data[2][y * frame->linesize[2] + x] = 64 + x + i * 5;
              }
          }
          frame->pts = i;
          /* encode the image */
          ret = avcodec_encode_video2(c, &pkt, frame, &got_output);
          if (ret < 0) {
              fprintf(stderr, "Error encoding frame\n");
              exit(1);
          }
          if (got_output) {
              printf("Write frame %3d (size=%5d)\n", i, pkt.size);
              fwrite(pkt.data, 1, pkt.size, f);
              av_free_packet(&pkt);
          }
      }
      /* get the delayed frames */
      for (got_output = 1; got_output; i++) {
          fflush(stdout);
          ret = avcodec_encode_video2(c, &pkt, NULL, &got_output);
          if (ret < 0) {
              fprintf(stderr, "Error encoding frame\n");
              exit(1);
          }
          if (got_output) {
              printf("Write frame %3d (size=%5d)\n", i, pkt.size);
              fwrite(pkt.data, 1, pkt.size, f);
              av_free_packet(&pkt);
          }
      }
      
      /////  Closes the file and finishes.....
      

1 个答案:

答案 0 :(得分:3)

延迟是固定的,因此您的编码器延迟永远不会超过delay帧。因此,随着记录长度的增加,内存消耗不会增加,因此没有问题,导致正确答案1:您只在编码结束时进行刷新。