LWJGL3: Switching screen mode triggers render() call
See original GitHub issueIssue details
If i try to toggle fullscreen mode while playing, i get an JVM crash.
Reproduction steps/code
Graphics.DisplayMode primaryMode = Gdx.graphics.getDisplayMode();
Gdx.graphics.setFullscreenMode(primaryMode);
Full Code:
//toggle fullscreen mode
if ((Gdx.input.isKeyPressed(Input.Keys.CONTROL_LEFT) || Gdx.input.isKeyPressed(Input.Keys.CONTROL_RIGHT)) && Gdx.input.isKeyJustPressed(Input.Keys.F)) {
//toggle fullscreen mode
if (Gdx.graphics.isFullscreen()) {
Gdx.graphics.setWindowedMode(this.lastWidth, this.lastHeight);
} else {
Graphics.DisplayMode primaryMode = Gdx.graphics.getDisplayMode();
Gdx.graphics.setFullscreenMode(primaryMode);
}
}
Version of LibGDX and/or relevant dependencies
Please provide the version(s) affected.
Stacktrace
#
# A fatal error has been detected by the Java Runtime Environment:
#
# EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x00007ffcbadcaceb, pid=10456, tid=1724
#
# JRE version: Java(TM) SE Runtime Environment (8.0_91-b15) (build 1.8.0_91-b15)
# Java VM: Java HotSpot(TM) 64-Bit Server VM (25.91-b15 mixed mode windows-amd64 compressed oops)
# Problematic frame:
# C [glfw.dll+0xaceb]
#
# Failed to write core dump. Minidumps are not enabled by default on client versions of Windows
#
# An error report file with more information is saved as:
# D:\Users\Justin\IdeaProjects\island-exploration-rts\hs_err_pid10456.log
#
# If you would like to submit a bug report, please visit:
# http://bugreport.java.com/bugreport/crash.jsp
# The crash happened outside the Java Virtual Machine in native code.
# See problematic frame for where to report the bug.
#
AL lib: (EE) alc_cleanup: 1 device not closed
Please select the affected platforms
- Android
- iOS (robovm)
- iOS (MOE)
- HTML/GWT
- Windows
- Linux
- MacOS
Issue Analytics
- State:
- Created 5 years ago
- Comments:5 (4 by maintainers)
Top Results From Across the Web
LWJGL 3 Not rendering anything, while successfully creating ...
To fix this, all I had to do is move glfwSwapBuffers(this.display) down to after the glPopMatrix() call. Here is how the loop() function ......
Read more >5 Ways to Avoid React Component Re-Renderings
1. Memoization using useMemo() and UseCallback() Hooks. Memoization enables your code to re-render components only if there's a change in the props. With...
Read more >Batch Rendering in LWJGL3 | Coding a 2D Game ... - YouTube
Join the Discord: https://discord.gg/4tHeAkxNg7I apologize in advance for this lengthy tutorial, unfortunately there is no easy way to ...
Read more >HUD · 3D Game Development with LWJGL 3 - GitBook
In this chapter we will create a HUD (Heads-Up Display) for our game. ... matrix is updated in each render call (because the...
Read more >3D Game Development with LWJGL 3
and the period at which the game is rendered to the screen. Why do we do this? ... Since the projection matrix won't...
Read more >
Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free
Top Related Reddit Thread
No results found
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
This is pretty interesting. What happened is clearly visible from the error log:
In your
render()
method, you have invokedsetFullscreenMode
, which made window fullscreen, which invoked GLFW resize callback, which in turn called yourrender()
method again (presumably so that resized window would show correctly rendered application), but because the key was still pressed, it invokedsetWindowedMode
, causing the cycle to repeat, alternating fullscreen and windowed mode, in single call stack. This probably lead to stack overflow, but maybe something else failed first.While it is indeed a problem caused by incorrect reading of input, for which your fix is correct, it is rather strange that changing windowed/fullscreen should reinvoke application’s
render()
inside itself. We may want to postpone its effects to the start of next frame (with explicit disabling ofrender()
invocation in framebuffer resize callback), so thatrender()
isn’t called twice, as these methods are usually not reentrant. For example, this crashes after pressing F:but someone may encounter this as a much subtler bug.
During normal window resizing, which happens through call to
GLFW.glfwPollEvents()
, normal rendering loop seems to stop, as it is blocked byGLFW.glfwPollEvents()
for the duration of window resize dragging (at least on Mac). I don’t know if this blocking is a bug or intended, but resizing the window triggers the resize callback, and the window never shows garbage (LWJGL2 did, IIRC), so it works well.However,
setFullscreen/WindowedMode
triggers the resize callback immediately, which, as it is usually called insiderender()
, causes nestedrender()
invocation. This is likely not desired behavior.Two ways to fix this come to mind:
setFullscreen/WindowedMode
is calledOption 1. feels more intuitive, but could still lead to bugs, as application may not expect screen resolution to change mid-frame. The frame may then still show incorrectly resized frame, as it is rendering for the original screen size. 2. therefore is probably more correct. Without any modifications to resize callback,
render()
would still get called twice per frame. I don’t know if GLFW expectsglfwSwapBuffers
to be called inside the callback, but if not, it may be worthwhile to disable therender()
call from the resize callback when it happens during window mode change, so that it doesn’t delay the whole operation.