uidriver/glfw: Enable to call SetWindowDecorated after Run

Fixes #556
This commit is contained in:
Hajime Hoshi 2019-11-26 11:45:52 +09:00
parent 995ba3afcf
commit e0d780b029
5 changed files with 29 additions and 24 deletions

View File

@ -18,7 +18,6 @@ package main
import ( import (
"bytes" "bytes"
"flag"
"fmt" "fmt"
"image" "image"
"image/color" "image/color"
@ -34,10 +33,6 @@ import (
"github.com/hajimehoshi/ebiten/inpututil" "github.com/hajimehoshi/ebiten/inpututil"
) )
var (
windowDecorated = flag.Bool("windowdecorated", true, "whether the window is decorated")
)
func init() { func init() {
rand.Seed(time.Now().UnixNano()) rand.Seed(time.Now().UnixNano())
} }
@ -81,6 +76,7 @@ func update(screen *ebiten.Image) error {
cursorVisible := ebiten.IsCursorVisible() cursorVisible := ebiten.IsCursorVisible()
vsyncEnabled := ebiten.IsVsyncEnabled() vsyncEnabled := ebiten.IsVsyncEnabled()
tps := ebiten.MaxTPS() tps := ebiten.MaxTPS()
decorated := ebiten.IsWindowDecorated()
if inpututil.IsKeyJustPressed(ebiten.KeyUp) { if inpututil.IsKeyJustPressed(ebiten.KeyUp) {
screenHeight += d screenHeight += d
@ -138,6 +134,9 @@ func update(screen *ebiten.Image) error {
panic("not reached") panic("not reached")
} }
} }
if inpututil.IsKeyJustPressed(ebiten.KeyD) {
decorated = !decorated
}
ebiten.SetScreenSize(screenWidth, screenHeight) ebiten.SetScreenSize(screenWidth, screenHeight)
ebiten.SetScreenScale(screenScale) ebiten.SetScreenScale(screenScale)
@ -146,6 +145,7 @@ func update(screen *ebiten.Image) error {
ebiten.SetCursorVisible(cursorVisible) ebiten.SetCursorVisible(cursorVisible)
ebiten.SetVsyncEnabled(vsyncEnabled) ebiten.SetVsyncEnabled(vsyncEnabled)
ebiten.SetMaxTPS(tps) ebiten.SetMaxTPS(tps)
ebiten.SetWindowDecorated(decorated)
if inpututil.IsKeyJustPressed(ebiten.KeyI) { if inpututil.IsKeyJustPressed(ebiten.KeyI) {
ebiten.SetWindowIcon([]image.Image{createRandomIconImage()}) ebiten.SetWindowIcon([]image.Image{createRandomIconImage()})
@ -180,6 +180,7 @@ Press C key to switch the cursor visibility
Press I key to change the window icon (only for desktops) Press I key to change the window icon (only for desktops)
Press V key to switch vsync Press V key to switch vsync
Press T key to switch TPS (ticks per second) Press T key to switch TPS (ticks per second)
Press D key to switch the window decoration
Cursor: (%d, %d) Cursor: (%d, %d)
TPS: Current: %0.2f / Max: %s TPS: Current: %0.2f / Max: %s
FPS: %0.2f FPS: %0.2f
@ -189,8 +190,6 @@ Device Scale Factor: %0.2f`, x, y, ebiten.CurrentTPS(), tpsStr, ebiten.CurrentFP
} }
func main() { func main() {
flag.Parse()
fmt.Printf("Device scale factor: %0.2f\n", ebiten.DeviceScaleFactor()) fmt.Printf("Device scale factor: %0.2f\n", ebiten.DeviceScaleFactor())
w, h := ebiten.ScreenSizeInFullscreen() w, h := ebiten.ScreenSizeInFullscreen()
fmt.Printf("Screen size in fullscreen: %d, %d\n", w, h) fmt.Printf("Screen size in fullscreen: %d, %d\n", w, h)
@ -212,8 +211,6 @@ func main() {
ebiten.SetWindowIcon([]image.Image{createRandomIconImage()}) ebiten.SetWindowIcon([]image.Image{createRandomIconImage()})
ebiten.SetWindowDecorated(*windowDecorated)
if err := ebiten.Run(update, initScreenWidth, initScreenHeight, initScreenScale, "Window Size (Ebiten Demo)"); err != nil { if err := ebiten.Run(update, initScreenWidth, initScreenHeight, initScreenScale, "Window Size (Ebiten Demo)"); err != nil {
log.Fatal(err) log.Fatal(err)
} }

View File

@ -94,6 +94,10 @@ func (w *Window) GetAttrib(attrib Hint) int {
return w.w.GetAttrib(glfw.Hint(attrib)) return w.w.GetAttrib(glfw.Hint(attrib))
} }
func (w *Window) SetAttrib(attrib Hint, value int) {
w.w.SetAttrib(glfw.Hint(attrib), value)
}
func (w *Window) GetCursorPos() (x, y float64) { func (w *Window) GetCursorPos() (x, y float64) {
return w.w.GetCursorPos() return w.w.GetCursorPos()
} }

View File

@ -114,6 +114,11 @@ func (w *Window) GetAttrib(attrib Hint) int {
return int(r) return int(r)
} }
func (w *Window) SetAttrib(attrib Hint, value int) {
glfwDLL.call("glfwSetWindowAttrib", w.w, uintptr(attrib), uintptr(value))
panicError()
}
func (w *Window) GetCursorPos() (x, y float64) { func (w *Window) GetCursorPos() (x, y float64) {
glfwDLL.call("glfwGetCursorPos", w.w, uintptr(unsafe.Pointer(&x)), uintptr(unsafe.Pointer(&y))) glfwDLL.call("glfwGetCursorPos", w.w, uintptr(unsafe.Pointer(&x)), uintptr(unsafe.Pointer(&y)))
panicError() panicError()

View File

@ -386,6 +386,7 @@ func (u *UserInterface) SetWindowTitle(title string) {
if !u.isRunning() { if !u.isRunning() {
return return
} }
u.title = title
_ = u.t.Call(func() error { _ = u.t.Call(func() error {
u.window.SetTitle(title) u.window.SetTitle(title)
return nil return nil
@ -503,19 +504,19 @@ func (u *UserInterface) SetWindowDecorated(decorated bool) {
return return
} }
panic("ui: SetWindowDecorated can't be called after Run so far.") _ = u.t.Call(func() error {
v := glfw.False
if decorated {
v = glfw.True
}
u.window.SetAttrib(glfw.Decorated, v)
// TODO: Now SetAttrib doesn't exist on GLFW 3.2. Revisit later (#556). // The title can be lost when the decoration is gone. Recover this.
// If SetAttrib exists, the implementation would be: if v == glfw.True {
// u.window.SetTitle(u.title)
// _ = u.t.Call(func() error { }
// v := glfw.False return nil
// if decorated { })
// v = glfw.True
// }
// })
// u.window.SetAttrib(glfw.Decorated, v)
// return nil
} }
func (u *UserInterface) IsWindowResizable() bool { func (u *UserInterface) IsWindowResizable() bool {
@ -649,7 +650,7 @@ func (u *UserInterface) run(width, height int, scale float64, title string, cont
// currentMonitor returns the monitor for the active window when possible and then the monitor for // currentMonitor returns the monitor for the active window when possible and then the monitor for
// the foreground window as fallback. In the current situation, the current window is hidden and // the foreground window as fallback. In the current situation, the current window is hidden and
// there is not the active window but the foreground window. After showing the current window, the // there is not the active window but the foreground window. After showing the current window, the
// current window will be the active window. Thus, currentMonitor retuls varies before and after // current window will be the active window. Thus, currentMonitor result varies before and after
// showing the window. // showing the window.
m := u.currentMonitor() m := u.currentMonitor()
mx, my := m.GetPos() mx, my := m.GetPos()

2
run.go
View File

@ -333,8 +333,6 @@ func IsRunnableInBackground() bool {
// SetWindowDecorated works only on desktops. // SetWindowDecorated works only on desktops.
// SetWindowDecorated does nothing on other platforms. // SetWindowDecorated does nothing on other platforms.
// //
// SetWindowDecorated panics if SetWindowDecorated is called after Run.
//
// SetWindowDecorated is concurrent-safe. // SetWindowDecorated is concurrent-safe.
func SetWindowDecorated(decorated bool) { func SetWindowDecorated(decorated bool) {
uiDriver().SetWindowDecorated(decorated) uiDriver().SetWindowDecorated(decorated)