@@ -16,6 +16,8 @@ var options = []flutter.Option{
16
16
type AppBarDraggable struct {
17
17
window * glfw.Window
18
18
windowDragActive chan bool
19
+ cursorPosY int
20
+ cursorPosX int
19
21
}
20
22
21
23
var _ flutter.Plugin = & AppBarDraggable {} // compile-time type check
@@ -27,7 +29,8 @@ func (p *AppBarDraggable) InitPlugin(messenger plugin.BinaryMessenger) error {
27
29
p .windowDragActive = make (chan bool )
28
30
channel := plugin .NewMethodChannel (messenger , "samples.go-flutter.dev/draggable" , plugin.StandardMethodCodec {})
29
31
channel .HandleFunc ("onPanStart" , p .onPanStart )
30
- channel .HandleFunc ("onPanEnd" , p .onPanEnd )
32
+ channel .HandleFuncSync ("onPanUpdate" , p .onPanUpdate ) // MUST RUN ON THE MAIN THREAD (use of HandleFuncSync)
33
+ channel .HandleFunc ("onClose" , p .onClose )
31
34
return nil
32
35
}
33
36
@@ -37,31 +40,31 @@ func (p *AppBarDraggable) InitPluginGLFW(window *glfw.Window) error {
37
40
return nil
38
41
}
39
42
40
- // onPanStart a golang / flutter implemantation of:
43
+ // onPanStart/onPanUpdate a golang / flutter implemantation of:
41
44
// "GLFW how to drag undecorated window without lag"
42
45
// https://stackoverflow.com/a/46205940
43
46
func (p * AppBarDraggable ) onPanStart (arguments interface {}) (reply interface {}, err error ) {
44
47
argumentsMap := arguments .(map [interface {}]interface {})
45
- cursorPosX := int (argumentsMap ["dx" ].(float64 ))
46
- cursorPosY := int (argumentsMap ["dy" ].(float64 ))
47
- for {
48
- select {
49
- case <- p .windowDragActive :
50
- return
51
- default :
52
- xpos , ypos := p .window .GetCursorPos ()
53
- deltaX := int (xpos ) - cursorPosX
54
- deltaY := int (ypos ) - cursorPosY
48
+ p .cursorPosX = int (argumentsMap ["dx" ].(float64 ))
49
+ p .cursorPosY = int (argumentsMap ["dy" ].(float64 ))
50
+ return nil , nil
51
+ }
52
+
53
+ // onPanUpdate calls GLFW functions that aren't thread safe.
54
+ // to run function on the main go-flutter thread, use HandleFuncSync instead of HandleFunc!
55
+ func (p * AppBarDraggable ) onPanUpdate (arguments interface {}) (reply interface {}, err error ) {
56
+ xpos , ypos := p .window .GetCursorPos () // This function must only be called from the main thread.
57
+ deltaX := int (xpos ) - p .cursorPosX
58
+ deltaY := int (ypos ) - p .cursorPosY
55
59
56
- x , y := p .window .GetPos ()
57
- p .window .SetPos (x + deltaX , y + deltaY )
58
- }
60
+ x , y := p .window .GetPos () // This function must only be called from the main thread.
61
+ p .window .SetPos (x + deltaX , y + deltaY ) // This function must only be called from the main thread.
59
62
60
- }
61
63
return nil , nil
62
64
}
63
65
64
- func (p * AppBarDraggable ) onPanEnd (arguments interface {}) (reply interface {}, err error ) {
65
- p .windowDragActive <- false
66
+ func (p * AppBarDraggable ) onClose (arguments interface {}) (reply interface {}, err error ) {
67
+ // This function may be called from any thread. Access is not synchronized.
68
+ p .window .SetShouldClose (true )
66
69
return nil , nil
67
70
}
0 commit comments