如何在iOS上的GPU上将3D SceneKit内容合成到视频帧上?
我正在开发AR应用程序。我有一个SceneKit场景被渲染成SCNView(使用OpenGL ES作为渲染API)。下面是另一个视图,显示相机的实时预览。我想创建一部包含视频和3D场景的电影如何在iOS上的GPU上将3D SceneKit内容合成到视频帧上?,ios,opengl-es,scenekit,core-video,Ios,Opengl Es,Scenekit,Core Video,我正在开发AR应用程序。我有一个SceneKit场景被渲染成SCNView(使用OpenGL ES作为渲染API)。下面是另一个视图,显示相机的实时预览。我想创建一部包含视频和3D场景的电影 我使用基于苹果RosyWriter示例代码的代码,用OpenGL着色器处理视频帧像素缓冲区。我认为我还没有完全理解这些概念,因为我不知道如何在视频帧上覆盖SceneKit渲染。我可以从SCNView/SCNSceneRenderer获得像素缓冲区吗?或者我需要使用SCNRender将场景重新渲染为OpenG
我使用基于苹果RosyWriter示例代码的代码,用OpenGL着色器处理视频帧像素缓冲区。我认为我还没有完全理解这些概念,因为我不知道如何在视频帧上覆盖SceneKit渲染。我可以从SCNView/SCNSceneRenderer获得像素缓冲区吗?或者我需要使用SCNRender将场景重新渲染为OpenGL捕获管道用于处理视频帧的屏幕外缓冲区中的纹理吗?在iOS 11中,现在有一种技术可以轻松地完成视频上的SceneKit叠加,但是一个完整的增强现实体验:。(此外,如果您正在滚动您自己的AR跟踪技术位,希望使用SceneKit显示,在iOS 11中,您可以将
AVCaptureDevice
设置为任何SceneKit材质属性的内容,包括场景背景。)
对于较旧的iOS版本,以下建议仍然适用
如果您已经有了使用OpenGL(或Metal)渲染的内容,并且希望向其中添加SceneKit内容,请使用
SCNRender
。像使用SCNView
一样在其上设置场景,以通常的方式执行所有现有的OpenGL渲染,然后调用rendertime:
只是为了证明概念,这里有一个非常快速的技巧,可以在上面添加SceneKit渲染。下面的所有代码都进入RosyWriterOpenGLRenderer.m
在实例变量的声明中:
@interface RosyWriterOpenGLRenderer ()
{
//... existing ivars, plus:
SCNRenderer *_scnRenderer;
}
在init
中,设置\u oglContext
后:
_scnRenderer = [SCNRenderer rendererWithContext:_oglContext options:nil];
SCNScene *scene = [SCNScene scene];
SCNNode *node = [SCNNode nodeWithGeometry:[SCNBox geometry]];
[node runAction:[SCNAction repeatActionForever:[SCNAction rotateByX:1 y:1 z:1 duration:1]]];
[scene.rootNode addChildNode:node];
_scnRenderer.scene = scene;
在copyrendedpixelbuffer
中,在对glFlush()
的现有调用和bail
标签之间:
glFlush();
[_scnRenderer renderAtTime:CFAbsoluteTimeGetCurrent()];
bail:
这足以在实时视频视图和录制的电影输出中获得一个旋转的白色立方体。(因为默认的材质和照明设置,所以它只是未着色的。对于真实的用例,请设置灯光、材质、相机、所需的几何体等。)
在iOS 11中,现在有了一种技术,不仅可以轻松地在视频上进行SceneKit叠加,还可以提供完整的增强现实体验:。(此外,如果您正在滚动您自己的AR跟踪技术位,希望使用SceneKit显示,在iOS 11中,您可以将
AVCaptureDevice
设置为任何SceneKit材质属性的内容,包括场景背景。)
对于较旧的iOS版本,以下建议仍然适用
如果您已经有了使用OpenGL(或Metal)渲染的内容,并且希望向其中添加SceneKit内容,请使用
SCNRender
。像使用SCNView
一样在其上设置场景,以通常的方式执行所有现有的OpenGL渲染,然后调用rendertime:
只是为了证明概念,这里有一个非常快速的技巧,可以在上面添加SceneKit渲染。下面的所有代码都进入RosyWriterOpenGLRenderer.m
在实例变量的声明中:
@interface RosyWriterOpenGLRenderer ()
{
//... existing ivars, plus:
SCNRenderer *_scnRenderer;
}
在init
中,设置\u oglContext
后:
_scnRenderer = [SCNRenderer rendererWithContext:_oglContext options:nil];
SCNScene *scene = [SCNScene scene];
SCNNode *node = [SCNNode nodeWithGeometry:[SCNBox geometry]];
[node runAction:[SCNAction repeatActionForever:[SCNAction rotateByX:1 y:1 z:1 duration:1]]];
[scene.rootNode addChildNode:node];
_scnRenderer.scene = scene;
在copyrendedpixelbuffer
中,在对glFlush()
的现有调用和bail
标签之间:
glFlush();
[_scnRenderer renderAtTime:CFAbsoluteTimeGetCurrent()];
bail:
这足以在实时视频视图和录制的电影输出中获得一个旋转的白色立方体。(因为默认的材质和照明设置,所以它只是未着色的。对于真实的用例,请设置灯光、材质、相机、所需的几何体等。)