/
StartHostButton.go
129 lines (105 loc) · 2.99 KB
/
StartHostButton.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
package host
import (
"fmt"
"os"
"runtime"
"syscall"
"unsafe"
"github.com/TKMAX777/RDPRelativeInput/debug"
"github.com/TKMAX777/RDPRelativeInput/winapi"
"github.com/lxn/win"
"github.com/pkg/errors"
)
// Create window on remote desktop client
func (h *Handler) StartHostButton() (win.HWND, error) {
type resultAttr struct {
hwnd win.HWND
err error
}
var result = make(chan resultAttr)
go func() {
const windowName = "RDP Input Wrapper"
// make win main function
debug.Debugf("GetModuleHandle...")
var hInstance = win.GetModuleHandle(nil)
if hInstance == win.HINSTANCE(0) {
debug.Debugln("err")
result <- resultAttr{win.HWND(winapi.NULL), errors.Errorf("GetModuleHandle: Failed to get handler: %d\n", win.GetLastError())}
return
}
debug.Debugln("ok")
var className = winapi.MustUTF16PtrFromString(windowName)
// lock os thread to avoid hanging GetMessage
runtime.LockOSThread()
defer runtime.UnlockOSThread()
var wClass win.WNDCLASSEX
wClass = win.WNDCLASSEX{
CbSize: uint32(unsafe.Sizeof(wClass)),
HInstance: hInstance,
// redraw when the window size changed
Style: win.CS_HREDRAW | win.CS_VREDRAW,
// set window background color to white
HbrBackground: win.HBRUSH(win.GetStockObject(win.WHITE_BRUSH)),
LpszClassName: className,
LpfnWndProc: syscall.NewCallback(h.getWindowProc()),
LpszMenuName: nil,
CbClsExtra: 0,
CbWndExtra: 0,
HIcon: win.HICON(winapi.NULL),
HCursor: win.HCURSOR(winapi.NULL),
HIconSm: win.HICON(winapi.NULL),
}
debug.Debugf("RegisterClassEx...")
if a := win.RegisterClassEx(&wClass); a == 0 {
debug.Debugln("err")
result <- resultAttr{win.HWND(winapi.NULL), errors.Errorf("RegisterClassEx: Failed to make window class \n")}
return
}
debug.Debugln("ok")
var windowNameUTF16 = winapi.MustUTF16PtrFromString(windowName)
debug.Debugf("CreateWindowEx...")
var hwnd = win.CreateWindowEx(
0,
className,
windowNameUTF16,
0,
50, 50, int32(50), int32(50),
win.HWND(winapi.NULL), win.HMENU(winapi.NULL), hInstance, unsafe.Pointer(nil),
)
if hwnd == win.HWND(winapi.NULL) {
debug.Debugln("err")
result <- resultAttr{hwnd, errors.Errorf("CreateWindowEx: Failed to make window")}
return
}
debug.Debugln("ok")
var style uint32 = uint32(win.WS_POPUP | win.WS_BORDER)
win.SetWindowLong(hwnd, win.GWL_STYLE, *(*int32)(unsafe.Pointer(&style)))
win.SetWindowPos(hwnd, 0, 50, 50, 50, 50, 0)
winapi.ShowWindow(hwnd, win.SW_SHOW)
winapi.UpdateWindow(hwnd)
h.captureHandler = &CaptureHandler{}
err := h.captureHandler.StartCapture(hwnd)
if err != nil {
fmt.Println(err)
}
h.isCapturing = true
result <- resultAttr{hwnd, nil}
for {
var msg win.MSG
switch win.GetMessage(&msg, hwnd, 0, 0) {
case 0:
debug.Debugln("Quit")
return
case -1:
os.Stderr.Write([]byte("CLOSE\n"))
os.Exit(0)
return
}
win.TranslateMessage(&msg)
win.DispatchMessage(&msg)
}
}()
var res = <-result
close(result)
return res.hwnd, res.err
}