开发者

How to enable VSYNC in D3D windowed app?

So, Im using D3D in a windowed application.

I inited D3D with the following parameters:

windowed: true;
backbufferformat: D3DFMT_X8R8G8B8;
presentinterval: D3DPRESENT_INTERVAL_ONE;
swapeffect: DISCARD

Each time OnPaint is called, I render the image to the backbuffer and present it to front.

As far as I know (and so does MSDN say), once I set D3DPRESENT_INTERVAL_ONE, vsync will work.

But in this case, the image is teared when dragging horizontally.

(It seems there's a line across the image, image below the line shows on the monitor and the above part follows.)

开发者_Python百科Some sites say D3DPRESENT_INTERVAL_ONE will not work in windowed applications.

How can I enable vsync anyway?

p.s. I finally found D3D vsync is enabled, while some window settings are not right that perhaps the window itself is not sync ed. though, I haven't peek the settings out.


I assume you're using D3D9? Should add that tag. On your D3DPRESENT_PARAMS variable:

if (bVysncEnabled)
{
    presentParams.PresentationInterval = D3DPRESENT_INTERVAL_ONE;
    presentParams.FullScreen_RefreshRateInHz = D3DPRESENT_RATE_DEFAULT;
}
else
{
    presentParams.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE;
    presentParams.FullScreen_RefreshRateInHz = 0;
}

If you've done this and you're using the old GDI stuff, it's not your vsync setting that's wrong, but the window settings. You must enable double buffering or you'll still get tearing.


You cannot vsync while in windowed, only in fullscreen. However, you could potentially ghetto it by getting info from the default display and finding the refresh rate, and then nerfing your renderer to only render at that rate...although I wouldn't suggest that route.


Windowed historically haven't been able to be vsynced for d3d, and only recently has this been possible, when aero is enabled in WinVista or Win7 and the app isn't running in presentation mode immidiate.


How often do you call ::OnPaint ? The reason I am asking is, that you must be calling ::OnPaint more often than the refresh rate of your attached monitor.

For me, I solved the refresh issue by forcing an ::OnPaint whenever the message loop is idle with invalidating the window. What will happen if you do that, is, that the RenderPresent command for D3D will WAIT until the graphic card finished rendering, which gives you a very precise timing of the ::OnPaint in sync with the actual monitor refresh rate !

I am having good success with this, and the statements above that windowed mode cannot vsync is definitely not true. Even in DirectX 9 Win XP, this just works.

Oh and last but not least, if you have more than one display attached, make sure to vsync with the actual display which presents your window. This seems a bit more tricky.


not exactly D3D, but AntiTearing.html describes how MPC-HC uses windowed EVR et al to try and avoid tearing of a windowed display. The links here: http://betterlogic.com/roger/2012/05/gdi-vsync-to-avoid-tearing/ may be useful for synchronizing, too (albeit something of a work around).

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜