2011-06-18 93 views
2

所以我需要的是简单的:想象一下,我们根本没有gui - ssh访问我们要构建和托管我们的应用的一些linux。该应用会生成视频流。我们有一些SDL应用程序和OpenGL着色器。我们所需要的就是像char *(大小为W * H * 3)那样得到渲染(就像我们通常在SDL窗口中看到的那样)如何做这样的事情?如何使SDL不会将其渲染到gui窗口中,而是放入可交换的指针中?SDL 1.3:如何渲染视频而不显示它?

回答

2

您不能直接渲染到OpenGL中的字节数组。

有两种方法来处理这个问题。第一种方法最简单,不需要上下文噱头,第二种方法。

首先,简单的方法。

为了使OpenGL正常工作,您需要有一个窗口。这并不意味着该窗口需要可见,但您需要创建一个才能获得有效的OpenGL上下文。因此第1步:创建一个窗口并将其最小化。

现在,为了获得有效的渲染,帧缓冲区中的像素必须通过“像素所有权测试”。渲染到保存屏幕本身的帧缓冲区时,屏幕上实际看不到的像素会使像素所有权测试失败。因此,如果您使用glReadPixels,那么这些像素的值是不确定的。

但是,这只适用于与窗口关联的默认帧缓冲区。帧缓冲区对象总是通过像素所有权测试。因此,第2步:根据需要创建帧缓冲区对象和相关的渲染缓冲区。

从那里,它非常简单。只需正常渲染,然后在想要获取数据时执行glReadPixels。 Pixel buffer objects可用于异步传输像素数据,如果性能是一个问题。 第3步:渲染并使用glReadPixels获取数据。


第二种方法是更广泛地提供(宗教组织需要扩展支持或OpenGL 3.0),但特定于平台的更多。

而不是在步骤2中创建一个FBO,而是你有步骤2:使用glXCreatePbuffer创建一个pbuffer。 pbuffer是一个屏幕渲染目标,其行为与默认帧缓冲区相同。您glXMakeContextCurrent告诉OpenGL渲染到pbuffer而不是默认的帧缓冲区。

步骤1和3与上面相同。

3

任何使用OpenGL都应该是硬件加速的,所以首先检查你的服务器是否有符合你的要求的GPU。如果您在租用的虚拟服务器或某个标准的根服务器上,那么您很可能没有GPU。

如果你有一个GPU,则有两种可能的方法:


方法1 - 简单的一个

你会(很遗憾)必须配置和启动X它的服务器这个X服务器也必须是当前的虚拟终端(即它必须是显卡上的主动事物)。然后,您将让正在运行该视频生成器的用户访问该X显示器(请参阅man xauth及其参考内容)

下一步是独立于SDL,它是OpenGL认为的:创建一个Framebuffer对象,呈现期望的图形;一个PBuffer也会工作,实际上我更喜欢这种情况,但是我发现Framebuffer Objects比当前Linux及其驱动程序上的PBuffers更可靠。

然后渲染此帧缓冲区对象或p缓冲器和往常一样和检索使用内容glReadPixels


方法2 - 灵活的一个

在较低水平,这是非常相似的方法1,但事情会为你抽象:获取VirtualGLhttp://www.virtualgl.org/在GPU上执行实际的OpenGL渲染。您不必在辅助X服务器上启动应用程序,而是直接使用提供的发送GLX流并获取JPEG图像流的VirtualGL服务器。您也可以使用运行虚拟帧缓冲区的辅助X服务器并持续捕捉该帧。或者可能是最优雅的:编写自己的X.Org视频驱动程序,将视频直接传送到视频流。