1

サンプルを Objective C から Monotouch に変換しようとしていますが、いくつかの問題に遭遇しました。

基本的には、ビデオ ファイルを読み取り、フレームを 1 つずつ opengl テクスチャにデコードしたいと考えています。

これを行うための鍵は AVAssetReader を使用することですが、Monotouch でこれを適切に設定する方法がわかりません。

これは私のコードです:

    AVUrlAsset asset=new AVUrlAsset(NSUrl.FromFilename(videoFileName),null);
    assetReader=new AVAssetReader(asset,System.IntPtr.Zero);
    AVAssetTrack videoTrack=asset.Tracks[0];
    NSDictionary videoSettings=new NSDictionary();

    NSString key = CVPixelBuffer.PixelFormatTypeKey;
    NSNumber val=0x754b9d0; //NSNumber* value = [NSNumber numberWithUnsignedInt:kCVPixelFormatType_32BGRA]; - Had to hardcode constant as it is not defined in Monotouch?

    videoSettings.SetNativeField(key,val);

//**The program crashes here:
    AVAssetReaderTrackOutput trackOutput=new AVAssetReaderTrackOutput(videoTrack,videoSettings);

    assetReader.AddOutput(trackOutput);
    assetReader.StartReading();

上記の行でプログラムがクラッシュし、無効な引数の例外が発生して、NSDictionary の内容が正しい形式ではないことが示されます。ビデオ ファイルを確認したところ、問題なく読み込まれました。「アセット」には、ビデオに関する有効な情報が含まれています。

これは元の Objective C コードです。

                NSString* key = (NSString*)kCVPixelBufferPixelFormatTypeKey;
                NSNumber* value = [NSNumber numberWithUnsignedInt:kCVPixelFormatType_32BGRA];
                NSDictionary* videoSettings = [NSDictionary dictionaryWithObject:value forKey:key];
                AVAssetReaderTrackOutput *trackOutput = [AVAssetReaderTrackOutput assetReaderTrackOutputWithTrack:videoTrack outputSettings:videoSettings];

                [_assetReader addOutput:trackOutput];
                [_assetReader startReading];

私は Objective C にはあまり興味がないので、助けていただければ幸いです。

編集:私は以下に提案されたコードを使用しました

var videoSettings = NSDictionary.FromObjectAndKey (
  new NSNumber ((int) MonoTouch.CoreVideo.CVPixelFormatType.CV32BGRA),
  MonoTouch.CoreVideo.CVPixelBuffer.PixelFormatTypeKey);

そして、プログラムはもはやクラッシュしません。次のコードを使用します。

        CMSampleBuffer buffer=assetReader.Outputs[0].CopyNextSampleBuffer();
        CVImageBuffer imageBuffer = buffer.GetImageBuffer();

ビデオ ファイルの次のフレームを含むイメージ バッファを取得します。imageBuffer オブジェクトを調べると、幅や高さなどの有効なデータがビデオ ファイルのデータと一致していることがわかりました。

しかし、imageBuffer BaseAddress は常に 0 です。これは、画像にデータがないことを示していますか? 私はテストとしてこれをやろうとしました:

        CVPixelBuffer buffer=(CVPixelBuffer)imageBuffer;
        CIImage image=CIImage.FromImageBuffer(buffer);

また、画像は常に null として返されます。これは、実際の画像データが存在せず、imageBuffer オブジェクトにフレーム ヘッダー情報のみが含まれているということですか?

もしそうなら、これは Monotouch のバグですか、それとも設定が間違っていますか?

画像データの準備が整うまで待つ必要があるのではないかと考えていましたが、その場合も方法がわかりません。今かなり立ち往生しています...

4

2 に答える 2

3

次のように NSDictionary を作成する必要があります。

var videoSettings = NSDictionary.FromObjectAndKey (
  new NSNumber ((int) MonoTouch.CoreVideo.CVPixelFormatType.CV32BGRA),
  MonoTouch.CoreVideo.CVPixelBuffer.PixelFormatTypeKey);

SetNativeFieldはまったく異なるものです (辞書にキーと値のペアを追加するのではなく、という名前のフィールドを に設定していますCVPixelBuffer.PixelFormatTypeKey) 。0x754b9d0

于 2012-01-20T01:37:20.830 に答える
1

[NSNumber numberWithUnsignedInt:kCVPixelFormatType_32BGRA]; - Monotouch で定義されていないため、定数をハードコードする必要がありましたか?

これを次のものに置き換えることができるはずです。

CVPixelFormatType.CV32BGRA

MonoTouch は、こ​​の値を0x42475241あなたのものとは異なるものとして定義することに注意してください。それはあなたの間違いかもしれません。そうでない場合は、小さな自己完結型のテスト ケースを作成し、http://bugzilla.xamarin.comのバグ レポートに添付して確認することをお勧めします。

利用可能な場合は、objective-c サンプルへのリンクも役立ちます (質問の更新またはバグ レポートへのリンクはこちら)。

于 2012-01-19T13:12:25.553 に答える