0

YUV フレーム (kCVPixelFormatType_420YpCbCr8BiPlanarVideoRange) を受け取り、CVPixelBufferRef から CIImage を作成すると、次のようになります。

CVPixelBufferRef が非 IOSurface でサポートされていないため、initWithCVPixelBuffer が失敗しました。

CVPixelBufferRef pixelBuffer;

size_t planeWidth[] = { width, width / 2 };
size_t planeHeight[] = { height, height / 2};
size_t planeBytesPerRow[] = { width, width / 2 };

CVReturn ret = CVPixelBufferCreateWithBytes(
kCFAllocatorDefault, width, height, kCVPixelFormatType_420YpCbCr8BiPlanarVideoRange,
data, bytesPerRow, 0, 0, 0, &pixelBuffer
);

if (ret != kCVReturnSuccess)
{
    NSLog(@"FAILED");

    CVPixelBufferRelease(pixelBuffer);

    return;
}

CVPixelBufferLockBaseAddress(pixelBuffer, 0);

// fails
CIImage * image = [[CIImage alloc] initWithCVPixelBuffer:pixelBuffer];

CVPixelBufferUnlockBaseAddress(pixelBuffer, 0);

CVPixelBufferRelease(pixelBuffer);

[image release];
4

1 に答える 1

7

「なぜこのエラーが発生するのですか?」という質問があると思います。

CVPixelBuffer IOSurface バッキングを作成するには、作成時に CVPixelBuffer のプロパティを設定する必要があります。現在、CVPixelBufferCreateWithBytes の最後から 2 番目のパラメータとして「0」を渡しています。

CVPixelBufferCreate で kCVPixelBufferIOSurfacePropertiesKey のキーと空の辞書である値 (デフォルトの IOSurface オプションを使用するため、その他は文書化されていません) を持つ辞書を渡します (CVPixelBufferCreateWithBytes で kCVPixelBufferIOSurfacePropertiesKey を使用できないため)、作成された CVPixelBuffer に正しいバイトをコピーします (don'バイトのアライメントを忘れてください)。それが、IOSurface でサポートする方法です。

ピクセル形式のため、すべてのエラーが削除されるかどうかはわかりませんが。私の理解では、100% 確実ではありませんが、GPU は、IOSurfaces として使用するために、そのピクセル形式でテクスチャを保持できる必要があります。

注: kCVPixelFormatType_420YpCbCr8BiPlanarVideoRange の正しいコピー ピクセル バイトは、この SO answer にあります。

于 2012-04-20T15:41:16.350 に答える