Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

glfwSwapBuffers does not block with swap interval > 0 when window is minimized or covered by another window #680

Closed
badlogic opened this issue Dec 31, 2015 · 10 comments
Assignees
Labels
Milestone

Comments

@badlogic
Copy link

@badlogic badlogic commented Dec 31, 2015

The docs of glfwSwapBuffers say that this call will vsync (to it's best ability in windowed mode i guess) if the swap interval is > 0.

This works if the window is partially visible (either full-screen or windowed mode). It actually doesn't "vsync" if the window is fully covered by another window or if the window is minimized. Is this by design? Only tested on Mac OS X.

I'm not sure if this could/should be "fixed" in GLFW or if it's the responsibility of the application to take care of it. However, it should at least be documented in the glfwSwapBuffers docs that no vsync'ing happens in case the window is fully covered or minimized.

@elmindreda

This comment has been minimized.

Copy link
Member

@elmindreda elmindreda commented Dec 31, 2015

That is by design, but it's Apple's design. OS X ignores the NSOpenGL swap interval when the window is obscured. No other OS does this.

I will look into working around this with display link at some point. If that doesn't work, I don't think there's anything GLFW can do.

@elmindreda

This comment has been minimized.

Copy link
Member

@elmindreda elmindreda commented Dec 31, 2015

I will add a note to the documentation for the next release.

@elmindreda elmindreda added this to the 3.2 milestone Dec 31, 2015
@elmindreda elmindreda self-assigned this Dec 31, 2015
@elmindreda elmindreda added the macOS label Dec 31, 2015
@meshula

This comment has been minimized.

Copy link

@meshula meshula commented Dec 31, 2015

This is an energy saving feature called App Nap. You need to disable it in applications that expect to do background processing such as render serving, or that should continue running when obscured. It can be accomplished from code, and would probably be a good option for glfw to expose. Look for App Nap on this page:

https://developer.apple.com/library/mac/releasenotes/MacOSX/WhatsNewInOSX/Articles/MacOSX10_9.html

@elmindreda

This comment has been minimized.

Copy link
Member

@elmindreda elmindreda commented Dec 31, 2015

That looks like yet another good candidate for the platform specific hints I'm sketching out.

@dmitshur

This comment has been minimized.

Copy link
Collaborator

@dmitshur dmitshur commented Jan 1, 2016

If App Nap is working as I understand, is this a problem? Hopefully, what's happening is that glfwSwapBuffers isn't blocking, but the app is still being suspended enough that the power savings are even greater than with just vsync.

Or did you want to disable that power saving functionality instead?

@meshula

This comment has been minimized.

Copy link

@meshula meshula commented Jan 1, 2016

If you implement a render server, for example, an application that creates images to be displayed on some other device, or just for screenshots, that application might run in the background. App Nap might suspend it. A primary reason to disable app nap is to enable server applications.

@badlogic

This comment has been minimized.

Copy link
Author

@badlogic badlogic commented Jan 2, 2016

My use case is to put the app mostly to sleep when obscured/minified. Doable from the application code itself. Thanks for the clarification @elmindreda!

@ithron

This comment has been minimized.

Copy link

@ithron ithron commented Aug 13, 2016

I think an application should suspend its rendering when the window is occluded. There is no point continue rendering when there is nothing to see.
But as far as I know there is no way to check the occlusion state with GLFW. Maybe one could change glfwGetWindowAttrib(window, GLFW_VISIBLE) to return 0 if the window is occluded?

When a window changes its occlusion state windowDidChangeOcclusionState:(NSNotification *) is called on the window delegate. I don't know if there is an easy way to check occasion state on there systems.

ithron added a commit to ithron/glfw that referenced this issue Aug 13, 2016
If a window is not hidden but occluded, e.g. by another window or the
window is on another screen/desktop that is currently not shown,
_glfwPlatformWindowVisible() returns 1 although the window is physically
not visible. This commit fixes this issue by treating occluded windows
as hidden, i.e. non visible.
Usage example:
When the render loop is limited by v-sync, glfwSwapBuffers() does not
block on OS X when AppNap is enabled and the window is occluded.
Therefore the application starts to burn CPU cycles althoug nothing is
displayed. With the fix in this commit the application could check if
the window is visible using glfwGetWindowAttrib(window, GLFW_VISIBLE)
and if the window is hidden (or occluded) it could pause the render
loop.
This is a workaround for issue glfw#680
ithron added a commit to ithron/glfw that referenced this issue Aug 14, 2016
If a window is not hidden but occluded, e.g. by another window or the
window is on another screen/desktop that is currently not shown,
_glfwPlatformWindowVisible() returns 1 although the window is physically
not visible. This commit fixes this issue by treating occluded windows
as hidden, i.e. non visible.
Usage example:
When the render loop is limited by v-sync, glfwSwapBuffers() does not
block on OS X when AppNap is enabled and the window is occluded.
Therefore the application starts to burn CPU cycles althoug nothing is
displayed. With the fix in this commit the application could check if
the window is visible using glfwGetWindowAttrib(window, GLFW_VISIBLE)
and if the window is hidden (or occluded) it could pause the render
loop.
This is a workaround for issue glfw#680
@claudiofantacci

This comment has been minimized.

Copy link

@claudiofantacci claudiofantacci commented Mar 22, 2017

I think an application should suspend its rendering when the window is occluded. There is no point continue rendering when there is nothing to see.

This is not always true.
Have a look at my use case here.

I will looking into this issue as well.
Maybe, I can be of help 😄

@elmindreda

This comment has been minimized.

Copy link
Member

@elmindreda elmindreda commented Mar 5, 2019

As a side-effect of fixing #1337, OpenGL vsync now uses a display link and is not affected by window occlusion.

nicobako added a commit to nicobako/glfw that referenced this issue Mar 20, 2019
This solution of one display link per window is far from ideal but is
still better than no solution.

As a side-effect this fixes swap interval breaking being ignored for
occluded windows on earlier versions of macOS.

Fixes glfw#680.
Fixes glfw#1337.
Related to glfw#1417.
Fixes glfw#1435.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
6 participants
You can’t perform that action at this time.