【发布时间】:2012-08-15 15:09:16
【问题描述】:
我想知道在使用 xlib 时如何使用eglSwapBuffers 正确启用 vsync。似乎对eglSwapInterval 的调用被忽略了。
我在窗口和全屏模式下运行。窗口模式是否可能根本不支持它?在这种情况下,降低渲染频率的好方法是什么(睡眠往往会导致不稳定的行为,因为无法保证何时醒来)。
【问题讨论】:
我想知道在使用 xlib 时如何使用eglSwapBuffers 正确启用 vsync。似乎对eglSwapInterval 的调用被忽略了。
我在窗口和全屏模式下运行。窗口模式是否可能根本不支持它?在这种情况下,降低渲染频率的好方法是什么(睡眠往往会导致不稳定的行为,因为无法保证何时醒来)。
【问题讨论】:
经过一番谷歌搜索,我终于找到了这个:
http://lists.freedesktop.org/archives/mesa-commit/2010-May/021020.html
egl:实现 EGL_NOK_swap_region
此扩展添加了一个新功能,它提供了一个替代方案 eglSwapBuffers。 eglSwapBuffersRegionNOK 接受两个新参数 除了 eglSwapBuffers 中的那些。新参数包括 指向定义矩形 (x, y, 宽度,高度)和一个整数,指定矩形的数量 列表。
并且 /usr/include/EGL/eglmesaext.h 声明
EGLAPI EGLBoolean EGLAPIENTRY eglSwapBuffersRegionNOK(EGLDisplay dpy, EGLSurface surface, EGLint numRects, const EGLint* rects);
这里还有一些用法示例:
https://github.com/blazt/piglit/blob/master/tests/egl/egl-nok-swap-region.c
所以我尝试这样使用它:
EGLint dirtyRect[4] = { 0, 0, 0, 0 };
PFNEGLSWAPBUFFERSREGIONNOK swap_buffers_region = (PFNEGLSWAPBUFFERSREGIONNOK)
eglGetProcAddress("eglSwapBuffersRegionNOK");
在我的窗口调整大小回调
dirtyRect[2] = windowWidth;
dirtyRect[3] = windowHeight;
在我的主循环中
if (swap_buffers_region)
swap_buffers_region(egl_dpy, egl_surf, 1, dirtyRect);
else
eglSwapBuffers(egl_dpy, egl_surf);
它确实看起来更流畅并且降低了帧速率,但仅下降到 180-200 FPS 的范围;所以我仍然需要在帧之间做一个睡眠。也许它只在关键 GPU 操作的一些短时间间隔内阻止交换缓冲区?或者,也许我做得不对。不确定。
【讨论】: