Swift - 如何将CVImageBufferRef转换为CVPixelBufferRef

kli*_*ger 7 swift

在objective-c中,您可以轻松地将CVImageBufferRef转换为CVPixelBufferRef:

CMSampleBufferRef sampleBuffer = some value

CVPixelBufferRef pixelBuffer = CMSampleBufferGetImageBuffer(sampleBuffer);
Run Code Online (Sandbox Code Playgroud)

我怎么能在swift中做到这一点?


var pixelBuffer : CVPixelBufferRef = CMSampleBufferGetImageBuffer(sampleBuffer)
Run Code Online (Sandbox Code Playgroud)

给出错误:'Unmanaged <CVPixelBufferRef>'不能转换为'CVPixelBufferRef'


var pixelBuffer : CVPixelBufferRef = CMSampleBufferGetImageBuffer(sampleBuffer).takeRetainedValue()
Run Code Online (Sandbox Code Playgroud)

给出错误:'CVImageBuffer'不能转换为'CVPixelBufferRef'


var pixelBuffer : CVPixelBufferRef = CMSampleBufferGetImageBuffer(sampleBuffer).takeRetainedValue() as CVPixelBufferRef
Run Code Online (Sandbox Code Playgroud)

给出错误:无法将表达式的类型'CVPixelBufferRef'转换为'CVPixelBufferRef'类型

Lom*_*baX 13

编辑

这个答案是在Swift beta测试期间给出的.现在似乎现在解决方案更简单了,正如克林格所说的那样

var pixelBuffer : CVPixelBuffer = CMSampleBufferGetImageBuffer(sampleBuffer)
Run Code Online (Sandbox Code Playgroud)

但是我会因历史原因留下以前的答案:-)

以前的答案

查看预发布文档:

https://developer.apple.com/library/prerelease/ios/documentation/Swift/Conceptual/BuildingCocoaApps/WorkingWithCocoaDataTypes.html#//apple_ref/doc/uid/TP40014216-CH6-XID_40

特别是这句话

重新映射的类型

当Swift导入Core Foundation类型时,编译器会重新映射这些类型的名称.编译器从每个类型名称的末尾删除Ref,因为所有Swift类都是引用类型,因此后缀是多余的.

Core Foundation CFTypeRef类型完全重映射为AnyObject类型.无论您在何处使用CFTypeRef,现在都应该在代码中使用AnyObject.

您要做的第一件事是从每种类型中删除"ref".但是没有必要,因为"refs"被类型化为"非ref"类型.

然后,这个陈述应该有效.在我从未使用过之前可能需要一些调整CMSampleBufferGetImageBuffer,因此我不确定第一行(初始化缓冲区)

    var buf : CMSampleBuffer = // initialize the buffer
    var anUnmanaged : Unmanaged<CVImageBuffer> = CMSampleBufferGetImageBuffer(buf)
    var returnValue = anUnmanaged.takeUnretainedValue()
Run Code Online (Sandbox Code Playgroud)

或者,很快

    var buf : CMSampleBuffer = // initialize the buffer
    var anUnmanaged : CVImageBuffer = CMSampleBufferGetImageBuffer(buf).takeRetainedValue()
Run Code Online (Sandbox Code Playgroud)

但是,您要求提供CVPixelBuffer.如果这两种类型是完全兼容的(我不知道底层的API,所以我假设在objc中CVPixelBuffer和CVImageBuffer之间的转换始终是安全的),没有"自动化"这样做,你必须通过一个不安全的指针.

完整的代码是这样的:

    var buf : CMSampleBuffer = // initialize the buffer
    var anUnmanaged : Unmanaged<CVImageBuffer> = CMSampleBufferGetImageBuffer(buf)
    var returnValue = anUnmanaged.takeUnretainedValue()

    var anOpaque = anUnmanaged.toOpaque()
    var pixelBuffer : CVPixelBuffer = Unmanaged<CVPixelBuffer>.fromOpaque(anOpaque).takeUnretainedValue()
Run Code Online (Sandbox Code Playgroud)

我使用了不使用保留计数的takeUnretainedValue(),因为CMSampleBufferGetImageBuffer()返回一个未保留的对象


kli*_*ger 5

在Xcode 6 beta 6中,这最终有效:

var pixelBuffer : CVPixelBuffer = CMSampleBufferGetImageBuffer(sampleBuffer)