如何以每秒60帧的速度录制屏幕外NSView



我想录制在macOS上运行的屏幕外NSView的视频输出(是否编码(。我确信没有API可以做到这一点,但我相信通过将其逐帧渲染到帧缓冲区中是可行的。

问题是我找不到以足够快的速度渲染视图的方法。我尝试过的方法没有成功(在运行蒙特利的MacBook M1 Pro上测试(:

  • [view dataWithPDFInsideRect:][view dataWithEPSInsideRect:]:执行大约需要200ms
  • [view.layer renderInContext:]:执行时间约为350ms
  • [view cacheDisplayInRect: toBitmapImageRep:]:执行时间约为100ms

我还尝试将视图嵌入到窗口中并捕获该窗口。窗口捕获功能(如CGWindowListCreateImage(要快得多,但在窗口不在屏幕上时不起作用。

考虑到视图可以在一个窗口中以60fps的速度渲染,为什么这些方法需要这么多时间?我是否错过了将NSView渲染到帧缓冲区的任何方法?

我终于找到了一种高性能的方法。通过这种方式捕捉视图,我可以达到60fps以上。

NSView* view = ...;
NSBitmapImageRep* bitmap = [
[NSBitmapImageRep alloc]
initWithBitmapDataPlanes:nil
pixelsWide:view.bounds.size.width
pixelsHigh:view.bounds.size.height
bitsPerSample:8
samplesPerPixel:4
hasAlpha:YES
isPlanar:NO
colorSpaceName:NSCalibratedRGBColorSpace
bitmapFormat:0
bytesPerRow:(4 * view.bounds.size.width)
bitsPerPixel:32
];
NSGraphicsContext* graphicsContext = [NSGraphicsContext graphicsContextWithBitmapImageRep:bitmap];
[NSGraphicsContext saveGraphicsState];
[NSGraphicsContext setCurrentContext:graphicsContext];
[view displayRectIgnoringOpacity:view.bounds inContext:graphicsContext];
[NSGraphicsContext restoreGraphicsState];
// pixels are in format [R, G, B, A, R, G, B, A, ...]
unsigned char* pixels = [bitmap bitmapData];

相关内容

  • 没有找到相关文章

最新更新