« レイヤー描画の方が軽いかも | メイン | 単純なVMR9モード »
2005年09月25日
吉里吉里 ムービー拡張日誌2:: オーバーレイでもセグメントループを
Tweet @jin1016をフォローVMR9を使えば複数の入力ストリームが扱えるので、ダミーストリームを作って、そこからデータが送られるタイミングでEC_UPDATEイベントを送ることによって、フレームの更新タイミングを取得すれば、セグメントループもピリオドイベントも使えるようになると考えていたが、そんなことをしなくてもインプレイスフィルタをレンダーの前に挿入して、そいつがEC_UPDATEイベントを送るようにすれば、更新タイミングを取得できることに気付いた。
描画周りの流れは……
フィルタのReceiveが呼び出されたらCTransInPlaceFilter::Receiveで、出力ピンにつながっている入力ピンのReceive を呼び出す。
入力ピンはレンダーのReceiveを呼び出し、
1. サンプルのレンダリングをスケジュールする (CBaseRenderer::PrepareReceive)。
2. スケジュールされた時間を待機する (CBaseRenderer::WaitForRenderTime)。
3. サンプルをレンダリングする (CBaseRenderer::Render)。
4. サンプルを解放する (CBaseRenderer::ClearPendingSample)。
という流れで処理する。
非同期で処理されている場合は、レンダリングされる前に返ってくる可能性があるが、その時は少しの誤差があるがあきらめることにする。
つまり、CTransInPlaceFilterを継承したクラスのReceiveで次のように書けばOKなはず。
HRESULT hr = CTransInPlaceFilter::Receive(pSample);
if( m_pSink )
m_pSink->Notify( EC_UPDATE, INT_MAX, NULL );
return hr;
後は、このフィルタをグラフ構築時にレンダーの前に突っ込んでやれば、レンダリング時にイベントが来るはず。
投稿者 Takenori : 2005年09月25日 22:55
comments powered by Disqus