mirror of
https://github.com/hajimehoshi/ebiten.git
synced 2024-11-10 04:57:26 +01:00
internal/uidriver/glfw: Bug fix: Adjust the window size along with the device scale
After this change, UserInterface's windowWidth and windowHeight are now windowWidthInDP and windowHeightInDP in device-independent pixels. Closes #1844
This commit is contained in:
parent
da5843c1eb
commit
57f3766a9c
@ -53,10 +53,10 @@ type UserInterface struct {
|
||||
title string
|
||||
window *glfw.Window
|
||||
|
||||
// windowWidth and windowHeight represents a window size.
|
||||
// The units are device-dependent pixels.
|
||||
windowWidth int
|
||||
windowHeight int
|
||||
// windowWidthInDP and windowHeightInDP represents a window size.
|
||||
// The units are device-independent pixels.
|
||||
windowWidthInDP int
|
||||
windowHeightInDP int
|
||||
|
||||
// The units are device-independent pixels.
|
||||
minWindowWidthInDP int
|
||||
@ -269,27 +269,6 @@ func (u *UserInterface) setRunning(running bool) {
|
||||
}
|
||||
}
|
||||
|
||||
func (u *UserInterface) getWindowSizeLimits() (minw, minh, maxw, maxh int) {
|
||||
u.m.RLock()
|
||||
defer u.m.RUnlock()
|
||||
|
||||
minw, minh, maxw, maxh = -1, -1, -1, -1
|
||||
m := u.currentMonitor()
|
||||
if u.minWindowWidthInDP >= 0 {
|
||||
minw = int(u.toGLFWPixel(float64(u.minWindowWidthInDP), m))
|
||||
}
|
||||
if u.minWindowHeightInDP >= 0 {
|
||||
minh = int(u.toGLFWPixel(float64(u.minWindowHeightInDP), m))
|
||||
}
|
||||
if u.maxWindowWidthInDP >= 0 {
|
||||
maxw = int(u.toGLFWPixel(float64(u.maxWindowWidthInDP), m))
|
||||
}
|
||||
if u.maxWindowHeightInDP >= 0 {
|
||||
maxh = int(u.toGLFWPixel(float64(u.maxWindowHeightInDP), m))
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
func (u *UserInterface) getWindowSizeLimitsInDP() (minw, minh, maxw, maxh int) {
|
||||
u.m.RLock()
|
||||
defer u.m.RUnlock()
|
||||
@ -452,7 +431,7 @@ func (u *UserInterface) setInitWindowPosition(x, y int) {
|
||||
u.initWindowPositionYInDP = y
|
||||
}
|
||||
|
||||
func (u *UserInterface) getInitWindowSize() (int, int) {
|
||||
func (u *UserInterface) getInitWindowSizeInDP() (int, int) {
|
||||
u.m.Lock()
|
||||
w, h := u.initWindowWidthInDP, u.initWindowHeightInDP
|
||||
u.m.Unlock()
|
||||
@ -576,8 +555,8 @@ func (u *UserInterface) SetFullscreen(fullscreen bool) {
|
||||
}
|
||||
|
||||
_ = u.t.Call(func() error {
|
||||
w, h := u.windowWidth, u.windowHeight
|
||||
u.setWindowSize(w, h, fullscreen)
|
||||
w, h := u.windowWidthInDP, u.windowHeightInDP
|
||||
u.setWindowSizeInDP(w, h, fullscreen)
|
||||
return nil
|
||||
})
|
||||
}
|
||||
@ -792,7 +771,9 @@ func (u *UserInterface) registerWindowSetSizeCallback() {
|
||||
|
||||
_ = u.t.Call(func() error {
|
||||
if width != 0 || height != 0 {
|
||||
u.setWindowSize(width, height, u.isFullscreen())
|
||||
w := int(u.fromGLFWPixel(float64(width), u.currentMonitor()))
|
||||
h := int(u.fromGLFWPixel(float64(height), u.currentMonitor()))
|
||||
u.setWindowSizeInDP(w, h, u.isFullscreen())
|
||||
}
|
||||
|
||||
outsideWidth, outsideHeight, outsideSizeChanged = u.updateSize()
|
||||
@ -890,10 +871,8 @@ func (u *UserInterface) init() error {
|
||||
u.setSizeCallbackEnabled = true
|
||||
|
||||
setSize := func() {
|
||||
ww, wh := u.getInitWindowSize()
|
||||
ww = int(u.toGLFWPixel(float64(ww), u.initMonitor))
|
||||
wh = int(u.toGLFWPixel(float64(wh), u.initMonitor))
|
||||
u.setWindowSize(ww, wh, u.isFullscreen())
|
||||
ww, wh := u.getInitWindowSizeInDP()
|
||||
u.setWindowSizeInDP(ww, wh, u.isFullscreen())
|
||||
}
|
||||
|
||||
// Set the window size and the window position in this order on Linux or other UNIX using X (#1118),
|
||||
@ -927,8 +906,8 @@ func (u *UserInterface) init() error {
|
||||
}
|
||||
|
||||
func (u *UserInterface) updateSize() (float64, float64, bool) {
|
||||
ww, wh := u.windowWidth, u.windowHeight
|
||||
u.setWindowSize(ww, wh, u.isFullscreen())
|
||||
ww, wh := u.windowWidthInDP, u.windowHeightInDP
|
||||
u.setWindowSizeInDP(ww, wh, u.isFullscreen())
|
||||
|
||||
if !u.toChangeSize {
|
||||
return 0, 0, false
|
||||
@ -947,9 +926,9 @@ func (u *UserInterface) updateSize() (float64, float64, bool) {
|
||||
w = u.fromGLFWMonitorPixel(float64(ww), m)
|
||||
h = u.fromGLFWMonitorPixel(float64(wh), m)
|
||||
} else {
|
||||
// Instead of u.windowWidth and u.windowHeight, use the actual window size here.
|
||||
// On Windows, the specified size at SetSize and the actual window size might not
|
||||
// match (#1163).
|
||||
// Instead of u.windowWidthInDP and u.windowHeightInDP, use the actual window size
|
||||
// here. On Windows, the specified size at SetSize and the actual window size might
|
||||
// not match (#1163).
|
||||
ww, wh := u.window.GetSize()
|
||||
w = u.fromGLFWPixel(float64(ww), u.currentMonitor())
|
||||
h = u.fromGLFWPixel(float64(wh), u.currentMonitor())
|
||||
@ -983,7 +962,9 @@ func (u *UserInterface) update() (float64, float64, bool, error) {
|
||||
|
||||
if u.isInitFullscreen() {
|
||||
w, h := u.window.GetSize()
|
||||
u.setWindowSize(w, h, true)
|
||||
ww := int(u.fromGLFWPixel(float64(w), u.currentMonitor()))
|
||||
wh := int(u.fromGLFWPixel(float64(h), u.currentMonitor()))
|
||||
u.setWindowSizeInDP(ww, wh, true)
|
||||
u.setInitFullscreen(false)
|
||||
}
|
||||
|
||||
@ -1160,25 +1141,6 @@ func (u *UserInterface) updateWindowSizeLimits() {
|
||||
u.window.SetSizeLimits(minw, minh, maxw, maxh)
|
||||
}
|
||||
|
||||
// adjustWindowSizeBasedOnSizeLimitsInDP adjust the size based on the window size limits.
|
||||
// width and height are in device-dependent pixels.
|
||||
func (u *UserInterface) adjustWindowSizeBasedOnSizeLimits(width, height int) (int, int) {
|
||||
minw, minh, maxw, maxh := u.getWindowSizeLimits()
|
||||
if minw >= 0 && width < minw {
|
||||
width = minw
|
||||
}
|
||||
if minh >= 0 && height < minh {
|
||||
height = minh
|
||||
}
|
||||
if maxw >= 0 && width > maxw {
|
||||
width = maxw
|
||||
}
|
||||
if maxh >= 0 && height > maxh {
|
||||
height = maxh
|
||||
}
|
||||
return width, height
|
||||
}
|
||||
|
||||
// adjustWindowSizeBasedOnSizeLimitsInDP adjust the size based on the window size limits.
|
||||
// width and height are in device-independent pixels.
|
||||
func (u *UserInterface) adjustWindowSizeBasedOnSizeLimitsInDP(width, height int) (int, int) {
|
||||
@ -1199,12 +1161,13 @@ func (u *UserInterface) adjustWindowSizeBasedOnSizeLimitsInDP(width, height int)
|
||||
}
|
||||
|
||||
// setWindowSize must be called from the main thread.
|
||||
func (u *UserInterface) setWindowSize(width, height int, fullscreen bool) {
|
||||
width, height = u.adjustWindowSizeBasedOnSizeLimits(width, height)
|
||||
func (u *UserInterface) setWindowSizeInDP(width, height int, fullscreen bool) {
|
||||
width, height = u.adjustWindowSizeBasedOnSizeLimitsInDP(width, height)
|
||||
|
||||
u.Graphics().SetFullscreen(fullscreen)
|
||||
|
||||
if u.windowWidth == width && u.windowHeight == height && u.isFullscreen() == fullscreen && u.lastDeviceScaleFactor == u.deviceScaleFactor(u.currentMonitor()) {
|
||||
scale := u.deviceScaleFactor(u.currentMonitor())
|
||||
if u.windowWidthInDP == width && u.windowHeightInDP == height && u.isFullscreen() == fullscreen && u.lastDeviceScaleFactor == scale {
|
||||
return
|
||||
}
|
||||
|
||||
@ -1215,7 +1178,7 @@ func (u *UserInterface) setWindowSize(width, height int, fullscreen bool) {
|
||||
height = 1
|
||||
}
|
||||
|
||||
u.lastDeviceScaleFactor = u.deviceScaleFactor(u.currentMonitor())
|
||||
u.lastDeviceScaleFactor = scale
|
||||
|
||||
// To make sure the current existing framebuffers are rendered,
|
||||
// swap buffers here before SetSize is called.
|
||||
@ -1232,13 +1195,13 @@ func (u *UserInterface) setWindowSize(width, height int, fullscreen bool) {
|
||||
}()
|
||||
}
|
||||
|
||||
windowRecreated := u.setWindowSizeImpl(width, height, fullscreen)
|
||||
windowRecreated := u.setWindowSizeInDPImpl(width, height, fullscreen)
|
||||
|
||||
u.adjustViewSize()
|
||||
|
||||
// As width might be updated, update windowWidth/Height here.
|
||||
u.windowWidth = width
|
||||
u.windowHeight = height
|
||||
u.windowWidthInDP = width
|
||||
u.windowHeightInDP = height
|
||||
|
||||
u.toChangeSize = true
|
||||
|
||||
@ -1249,7 +1212,7 @@ func (u *UserInterface) setWindowSize(width, height int, fullscreen bool) {
|
||||
}
|
||||
}
|
||||
|
||||
func (u *UserInterface) setWindowSizeImpl(width, height int, fullscreen bool) bool {
|
||||
func (u *UserInterface) setWindowSizeInDPImpl(width, height int, fullscreen bool) bool {
|
||||
var windowRecreated bool
|
||||
|
||||
if fullscreen {
|
||||
@ -1275,7 +1238,7 @@ func (u *UserInterface) setWindowSizeImpl(width, height int, fullscreen bool) bo
|
||||
// On Windows, giving a too small width doesn't call a callback (#165).
|
||||
// To prevent hanging up, return asap if the width is too small.
|
||||
// 126 is an arbitrary number and I guess this is small enough.
|
||||
minWindowWidth := int(u.toGLFWPixel(126, u.currentMonitor()))
|
||||
minWindowWidth := 126
|
||||
if u.window.GetAttrib(glfw.Decorated) == glfw.False {
|
||||
minWindowWidth = 1
|
||||
}
|
||||
@ -1290,7 +1253,9 @@ func (u *UserInterface) setWindowSizeImpl(width, height int, fullscreen bool) bo
|
||||
// When OpenGL is used, swapping buffer is enough to solve the image-lag
|
||||
// issue (#1004). Rather, recreating window destroys GPU resources.
|
||||
// TODO: This might not work when vsync is disabled.
|
||||
u.window.SetMonitor(nil, 0, 0, width, height, 0)
|
||||
ww := int(u.toGLFWPixel(float64(width), u.currentMonitor()))
|
||||
wh := int(u.toGLFWPixel(float64(height), u.currentMonitor()))
|
||||
u.window.SetMonitor(nil, 0, 0, ww, wh, 0)
|
||||
glfw.PollEvents()
|
||||
u.swapBuffers()
|
||||
} else {
|
||||
@ -1325,8 +1290,8 @@ func (u *UserInterface) setWindowSizeImpl(width, height int, fullscreen bool) bo
|
||||
// Set the window size after the position. The order matters.
|
||||
// In the opposite order, the window size might not be correct when going back from fullscreen with multi monitors.
|
||||
oldW, oldH := u.window.GetSize()
|
||||
newW := width
|
||||
newH := height
|
||||
newW := int(u.toGLFWPixel(float64(width), u.currentMonitor()))
|
||||
newH := int(u.toGLFWPixel(float64(height), u.currentMonitor()))
|
||||
if oldW != newW || oldH != newH {
|
||||
u.framebufferSizeCallbackCh = make(chan struct{}, 1)
|
||||
if u.framebufferSizeCallback == 0 {
|
||||
@ -1537,7 +1502,9 @@ func (u *UserInterface) maximizeWindow() {
|
||||
// Do not call setWindowSize in the fullscreen mode since setWindowSize requires the window size
|
||||
// before the fullscreen, while window.GetSize() returns the desktop screen size in the fullscreen mode.
|
||||
w, h := u.window.GetSize()
|
||||
u.setWindowSize(w, h, u.isFullscreen())
|
||||
ww := int(u.fromGLFWPixel(float64(w), u.currentMonitor()))
|
||||
wh := int(u.fromGLFWPixel(float64(h), u.currentMonitor()))
|
||||
u.setWindowSizeInDP(ww, wh, u.isFullscreen())
|
||||
}
|
||||
}
|
||||
|
||||
@ -1588,7 +1555,9 @@ func (u *UserInterface) restoreWindow() {
|
||||
// before the fullscreen, while window.GetSize() returns the desktop screen size in the fullscreen mode.
|
||||
if !u.isFullscreen() {
|
||||
w, h := u.window.GetSize()
|
||||
u.setWindowSize(w, h, u.isFullscreen())
|
||||
ww := int(u.fromGLFWPixel(float64(w), u.currentMonitor()))
|
||||
wh := int(u.fromGLFWPixel(float64(h), u.currentMonitor()))
|
||||
u.setWindowSizeInDP(ww, wh, u.isFullscreen())
|
||||
}
|
||||
}
|
||||
|
||||
@ -1670,7 +1639,9 @@ func (u *UserInterface) setWindowPosition(x, y int, monitor *glfw.Monitor) {
|
||||
// before the fullscreen, while window.GetSize() returns the desktop screen size in the fullscreen mode.
|
||||
if !u.isFullscreen() && runtime.GOOS == "darwin" {
|
||||
w, h := u.window.GetSize()
|
||||
u.setWindowSize(w, h, u.isFullscreen())
|
||||
ww := int(u.fromGLFWPixel(float64(w), u.currentMonitor()))
|
||||
wh := int(u.fromGLFWPixel(float64(h), u.currentMonitor()))
|
||||
u.setWindowSizeInDP(ww, wh, u.isFullscreen())
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -206,13 +206,13 @@ func (w *window) SetPosition(x, y int) {
|
||||
|
||||
func (w *window) Size() (int, int) {
|
||||
if !w.ui.isRunning() {
|
||||
ww, wh := w.ui.getInitWindowSize()
|
||||
ww, wh := w.ui.getInitWindowSizeInDP()
|
||||
return w.ui.adjustWindowSizeBasedOnSizeLimitsInDP(ww, wh)
|
||||
}
|
||||
ww, wh := 0, 0
|
||||
_ = w.ui.t.Call(func() error {
|
||||
ww = int(w.ui.fromGLFWPixel(float64(w.ui.windowWidth), w.ui.currentMonitor()))
|
||||
wh = int(w.ui.fromGLFWPixel(float64(w.ui.windowHeight), w.ui.currentMonitor()))
|
||||
ww = w.ui.windowWidthInDP
|
||||
wh = w.ui.windowHeightInDP
|
||||
return nil
|
||||
})
|
||||
return ww, wh
|
||||
@ -230,9 +230,7 @@ func (w *window) SetSize(width, height int) {
|
||||
return nil
|
||||
}
|
||||
|
||||
ww := int(w.ui.toGLFWPixel(float64(width), w.ui.currentMonitor()))
|
||||
wh := int(w.ui.toGLFWPixel(float64(height), w.ui.currentMonitor()))
|
||||
w.ui.setWindowSize(ww, wh, w.ui.isFullscreen())
|
||||
w.ui.setWindowSizeInDP(width, height, w.ui.isFullscreen())
|
||||
return nil
|
||||
})
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user