質問

How to writeビットマップとしてフレームOgg Theora C\C++?

一部の事例がソースのう坊!)

役に立ちましたか?

解決

これが次のとおりです libtheora api例コード.

これが次のとおりです マイクロハウツー それは、Theoraバイナリの使用方法を示しています。エンコーダーが読み取るように ビデオ用の生、圧縮されていない「yuv4mpeg」データ ビデオフレームをエンコーダーに配管することで、アプリからも使用できます。

他のヒント

全体の溶液を少し長めとしてここにコード例では、そのままダウンロードlibtheoraからXiph.orgある例png2theora.すべての図書館の機能をこれからもこの文書Xiph.org のためのtheoraおよびogg.

  1. コth_info_init()をinitialise、th_info構造設計では出力パラメータを格を会員とのこと。
  2. 使用する構造を呼び出th_encode_alloc()をエンコーダの文脈
  3. Initialise、ogg、ストリームとogg_stream_init()
  4. Initialise空th_comment構造を用いth_comment_init

繰り返し処理を実行し以下の通り:

  1. コth_encode_flushheaderのエンコーダのコンテキストは空白のコメント構造ogg_packet.
  2. 送信のパケットの開発ストリームogg_stream_packetin()

まth_encode_flushheader0を返します(エラーコード)

現在、繰り返し呼ogg_stream_pageout()、文書のページです。ヘッダやそのページです。体への出力ファイルまで、0を返します。今コogg_stream_flush書のページのファイルです。

きを書くことができるフレームのエンコーダを用いております。ここではどのよう"とか"また戻ってしまった:

int theora_write_frame(int outputFd, unsigned long w, unsigned long h, unsigned char *yuv_y, unsigned char *yuv_u, unsigned char *yuv_v, int last)
{
  th_ycbcr_buffer ycbcr;
  ogg_packet op;
  ogg_page og;

  unsigned long yuv_w;
  unsigned long yuv_h;

  /* Must hold: yuv_w >= w */
  yuv_w = (w + 15) & ~15;
  /* Must hold: yuv_h >= h */
  yuv_h = (h + 15) & ~15;

  //Fill out the ycbcr buffer
  ycbcr[0].width = yuv_w;
  ycbcr[0].height = yuv_h;
  ycbcr[0].stride = yuv_w;
  ycbcr[1].width = yuv_w;
  ycbcr[1].stride = ycbcr[1].width;
  ycbcr[1].height = yuv_h;
  ycbcr[2].width = ycbcr[1].width;
  ycbcr[2].stride = ycbcr[1].stride;
  ycbcr[2].height = ycbcr[1].height;

  if(encoderInfo->pixel_fmt == TH_PF_420)
  {
    //Chroma is decimated by 2 in both directions
    ycbcr[1].width = yuv_w >> 1;
    ycbcr[2].width = yuv_w >> 1;
    ycbcr[1].height = yuv_h >> 1;
    ycbcr[2].height = yuv_h >> 1;
  }else if(encoderInfo->pixel_fmt == TH_PF_422)
  {
    ycbcr[1].width = yuv_w >> 1;
    ycbcr[2].width = yuv_w >> 1;
  }else if(encoderInfo->pixel_fmt != TH_PF_422)
  {
    //Then we have an unknown pixel format
    //We don't know how long the arrays are!
    fprintf(stderr, "[theora_write_frame] Unknown pixel format in writeFrame!\n");
    return -1;
  }

  ycbcr[0].data = yuv_y;
  ycbcr[1].data = yuv_u;
  ycbcr[2].data = yuv_v;

  /* Theora is a one-frame-in,one-frame-out system; submit a frame
     for compression and pull out the packet */
  if(th_encode_ycbcr_in(encoderContext, ycbcr)) {
    fprintf(stderr, "[theora_write_frame] Error: could not encode frame\n");
    return -1;
  }

  if(!th_encode_packetout(encoderContext, last, &op)) {
    fprintf(stderr, "[theora_write_frame] Error: could not read packets\n");
    return -1;
  }

  ogg_stream_packetin(&theoraStreamState, &op);
  ssize_t bytesWritten = 0;
  int pagesOut = 0;
  while(ogg_stream_pageout(&theoraStreamState, &og)) {
    pagesOut ++;
    bytesWritten = write(outputFd, og.header, og.header_len);
    if(bytesWritten != og.header_len)
    {
      fprintf(stderr, "[theora_write_frame] Error: Could not write to file\n");
      return -1;
    }
    bytesWritten = write(outputFd, og.body, og.body_len);
    if(bytesWritten != og.body_len)
    {
      bytesWritten = fprintf(stderr, "[theora_write_frame] Error: Could not write to file\n");
      return -1;
    }
  }
  return pagesOut;
}

がencoderInfoのth_info構造用initialiseのエンコーダ(静的にデータセクション。

に、最後のフレーム設定の最後のフレームth_encode_packetout()となくストリームを終了します。

一度行われ、必ず清掃(最終fd中).th_info_clear()は明らかにth_info構造th_encode_free()は無料でごエンコーダコンテキスト

明らかにする必要がありま換されたビットマップへのYUV面前を渡すことができてtheora_write_frame().

今日の一部です。幸運を祈っています。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top