Macos AvasseTraderTrackOutput有时提供空白视频帧
我正在编写一个应用程序,它使用AVKit读取一个视频文件,并对每个帧进行处理,最后生成一个输出图像 首先,我加载资源,将Macos AvasseTraderTrackOutput有时提供空白视频帧,macos,cocoa,video,Macos,Cocoa,Video,我正在编写一个应用程序,它使用AVKit读取一个视频文件,并对每个帧进行处理,最后生成一个输出图像 首先,我加载资源,将avurlassetpreferprecurisedurationandTIMINGKEY设置为YES,然后找到第一个视频曲目,并创建一个资产读取器和一个资产读取器输出,其解压设置设置为kCVPixelFormatType_32BGRA——根据文档,这是此处少数允许的值之一 然后我在一个循环中调用copyNextSampleBuffer,并对得到的CMSampleBufferR
avurlassetpreferprecurisedurationandTIMINGKEY
设置为YES
,然后找到第一个视频曲目,并创建一个资产读取器和一个资产读取器输出,其解压设置设置为kCVPixelFormatType_32BGRA
——根据文档,这是此处少数允许的值之一
然后我在一个循环中调用copyNextSampleBuffer
,并对得到的CMSampleBufferRef
执行以下操作:
CVImageBufferRef movieFrame = CMSampleBufferGetImageBuffer(sampleBuffer);
NSCIImageRep *imageRep = [NSCIImageRep
imageRepWithCIImage:[CIImage imageWithCVImageBuffer:movieFrame]];
NSImage *image = [[NSImage alloc] initWithSize:[imageRep size]];
[image addRepresentation:imageRep];
在大多数情况下,这很好。然而,有些视频偶尔会生成空白帧,还有一些视频的每一帧都是空白的。我是不是犯了什么明显的错误?嗯,我最终解决了这个问题。偶尔出现的空白帧是由于线程问题造成的,通过使用以下方法创建NSImage解决了始终空白帧的问题:
CVPixelBufferLockBaseAddress(movieFrame,0);
uint8_t *baseAddress = (uint8_t *)CVPixelBufferGetBaseAddress(movieFrame);
size_t bytesPerRow = CVPixelBufferGetBytesPerRow(movieFrame);
size_t width = CVPixelBufferGetWidth(movieFrame);
size_t height = CVPixelBufferGetHeight(movieFrame);
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef newContext = CGBitmapContextCreate(baseAddress,
width, height, 8,
bytesPerRow,
colorSpace,
kCGBitmapByteOrder32Little |
kCGImageAlphaNoneSkipFirst);
CGImageRef frame = CGBitmapContextCreateImage(newContext);
CVPixelBufferUnlockBaseAddress(movieFrame,0);
CGContextRelease(newContext);
CGColorSpaceRelease(colorSpace);
NSImage *image = [[NSImage alloc] initWithCGImage:frame size:NSMakeSize(width,height)];
CGImageRelease(frame);
我希望我能理解为什么,但至少它现在起作用了