Refactor (windows).

This commit is contained in:
Nuno Cruces 2022-06-20 16:05:11 +01:00
parent 3aa09ad7bb
commit 6df549b1f0
12 changed files with 378 additions and 301 deletions

View file

@ -27,12 +27,12 @@ type calendarDialog struct {
out time.Time
err error
wnd uintptr
textCtl uintptr
dateCtl uintptr
okBtn uintptr
cancelBtn uintptr
extraBtn uintptr
wnd win.HWND
textCtl win.HWND
dateCtl win.HWND
okBtn win.HWND
cancelBtn win.HWND
extraBtn win.HWND
font font
}
@ -59,36 +59,36 @@ func (dlg *calendarDialog) setup(text string, opts options) (time.Time, error) {
defer win.UnregisterClass(cls, instance)
owner, _ := opts.attach.(win.HWND)
dlg.wnd, _, _ = createWindowEx.Call(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
uintptr(cls), strptr(*opts.title),
dlg.wnd, _ = win.CreateWindowEx(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
cls, strptr(*opts.title),
_WS_POPUPWINDOW|_WS_CLIPSIBLINGS|_WS_DLGFRAME,
_CW_USEDEFAULT, _CW_USEDEFAULT,
281, 281, uintptr(owner), 0, uintptr(instance), uintptr(unsafe.Pointer(dlg)))
281, 281, owner, 0, instance, unsafe.Pointer(dlg))
dlg.textCtl, _, _ = createWindowEx.Call(0,
dlg.textCtl, _ = win.CreateWindowEx(0,
strptr("STATIC"), strptr(text),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_SS_WORDELLIPSIS|_SS_EDITCONTROL|_SS_NOPREFIX,
12, 10, 241, 16, dlg.wnd, 0, uintptr(instance), 0)
12, 10, 241, 16, dlg.wnd, 0, instance, nil)
var flags uintptr = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _MCS_NOTODAY
dlg.dateCtl, _, _ = createWindowEx.Call(0,
var flags uint32 = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _MCS_NOTODAY
dlg.dateCtl, _ = win.CreateWindowEx(0,
strptr(_MONTHCAL_CLASS),
0, flags,
12, 30, 241, 164, dlg.wnd, 0, uintptr(instance), 0)
nil, flags,
12, 30, 241, 164, dlg.wnd, 0, instance, nil)
dlg.okBtn, _, _ = createWindowEx.Call(0,
dlg.okBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.okLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP|_BS_DEFPUSHBUTTON,
12, 206, 75, 24, dlg.wnd, win.IDOK, uintptr(instance), 0)
dlg.cancelBtn, _, _ = createWindowEx.Call(0,
12, 206, 75, 24, dlg.wnd, win.IDOK, instance, nil)
dlg.cancelBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.cancelLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 206, 75, 24, dlg.wnd, win.IDCANCEL, uintptr(instance), 0)
12, 206, 75, 24, dlg.wnd, win.IDCANCEL, instance, nil)
if opts.extraButton != nil {
dlg.extraBtn, _, _ = createWindowEx.Call(0,
dlg.extraBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.extraButton),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 206, 75, 24, dlg.wnd, win.IDNO, uintptr(instance), 0)
12, 206, 75, 24, dlg.wnd, win.IDNO, instance, nil)
}
if opts.time != nil {
@ -97,13 +97,13 @@ func (dlg *calendarDialog) setup(text string, opts options) (time.Time, error) {
date.year = uint16(year)
date.month = uint16(month)
date.day = uint16(day)
sendMessage.Call(dlg.dateCtl, win.MCM_SETCURSEL, 0, uintptr(unsafe.Pointer(&date)))
win.SendMessagePointer(dlg.dateCtl, win.MCM_SETCURSEL, 0, unsafe.Pointer(&date))
}
dlg.layout(getDPI(dlg.wnd))
centerWindow(dlg.wnd)
setFocus.Call(dlg.dateCtl)
showWindow.Call(dlg.wnd, _SW_NORMAL, 0)
win.SetFocus(dlg.dateCtl)
win.ShowWindow(dlg.wnd, _SW_NORMAL)
if opts.ctx != nil {
wait := make(chan struct{})
@ -111,7 +111,7 @@ func (dlg *calendarDialog) setup(text string, opts options) (time.Time, error) {
go func() {
select {
case <-opts.ctx.Done():
sendMessage.Call(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
win.SendMessage(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
case <-wait:
}
}()
@ -128,21 +128,21 @@ func (dlg *calendarDialog) setup(text string, opts options) (time.Time, error) {
func (dlg *calendarDialog) layout(dpi dpi) {
font := dlg.font.forDPI(dpi)
sendMessage.Call(dlg.textCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.dateCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.okBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.cancelBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.extraBtn, win.WM_SETFONT, font, 1)
setWindowPos.Call(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(281), _SWP_NOZORDER|_SWP_NOMOVE)
setWindowPos.Call(dlg.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
setWindowPos.Call(dlg.dateCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(164), _SWP_NOZORDER)
win.SendMessage(dlg.textCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.dateCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.okBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.cancelBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.extraBtn, win.WM_SETFONT, font, 1)
win.SetWindowPos(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(281), _SWP_NOZORDER|_SWP_NOMOVE)
win.SetWindowPos(dlg.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
win.SetWindowPos(dlg.dateCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(164), _SWP_NOZORDER)
if dlg.extraBtn == 0 {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
} else {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(12), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(12), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
}
}
@ -172,7 +172,7 @@ func calendarProc(wnd uintptr, msg uint32, wparam uintptr, lparam *unsafe.Pointe
return 1
case win.IDOK, win.IDYES:
var date _SYSTEMTIME
sendMessage.Call(dlg.dateCtl, win.MCM_GETCURSEL, 0, uintptr(unsafe.Pointer(&date)))
win.SendMessagePointer(dlg.dateCtl, win.MCM_GETCURSEL, 0, unsafe.Pointer(&date))
dlg.out = time.Date(int(date.year), time.Month(date.month), int(date.day), 0, 0, 0, 0, time.UTC)
case win.IDCANCEL:
dlg.err = ErrCanceled

View file

@ -26,12 +26,12 @@ type entryDialog struct {
out string
err error
wnd uintptr
textCtl uintptr
editCtl uintptr
okBtn uintptr
cancelBtn uintptr
extraBtn uintptr
wnd win.HWND
textCtl win.HWND
editCtl win.HWND
okBtn win.HWND
cancelBtn win.HWND
extraBtn win.HWND
font font
}
@ -58,46 +58,46 @@ func (dlg *entryDialog) setup(text string, opts options) (string, error) {
defer win.UnregisterClass(cls, instance)
owner, _ := opts.attach.(win.HWND)
dlg.wnd, _, _ = createWindowEx.Call(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
uintptr(cls), strptr(*opts.title),
dlg.wnd, _ = win.CreateWindowEx(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
cls, strptr(*opts.title),
_WS_POPUPWINDOW|_WS_CLIPSIBLINGS|_WS_DLGFRAME,
_CW_USEDEFAULT, _CW_USEDEFAULT,
281, 141, uintptr(owner), 0, uintptr(instance), uintptr(unsafe.Pointer(dlg)))
281, 141, owner, 0, instance, unsafe.Pointer(dlg))
dlg.textCtl, _, _ = createWindowEx.Call(0,
dlg.textCtl, _ = win.CreateWindowEx(0,
strptr("STATIC"), strptr(text),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_SS_WORDELLIPSIS|_SS_EDITCONTROL|_SS_NOPREFIX,
12, 10, 241, 16, dlg.wnd, 0, uintptr(instance), 0)
12, 10, 241, 16, dlg.wnd, 0, instance, nil)
var flags uintptr = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _ES_AUTOHSCROLL
var flags uint32 = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _ES_AUTOHSCROLL
if opts.hideText {
flags |= _ES_PASSWORD
}
dlg.editCtl, _, _ = createWindowEx.Call(_WS_EX_CLIENTEDGE,
dlg.editCtl, _ = win.CreateWindowEx(_WS_EX_CLIENTEDGE,
strptr("EDIT"), strptr(opts.entryText),
flags,
12, 30, 241, 24, dlg.wnd, 0, uintptr(instance), 0)
12, 30, 241, 24, dlg.wnd, 0, instance, nil)
dlg.okBtn, _, _ = createWindowEx.Call(0,
dlg.okBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.okLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP|_BS_DEFPUSHBUTTON,
12, 66, 75, 24, dlg.wnd, win.IDOK, uintptr(instance), 0)
dlg.cancelBtn, _, _ = createWindowEx.Call(0,
12, 66, 75, 24, dlg.wnd, win.IDOK, instance, nil)
dlg.cancelBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.cancelLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 66, 75, 24, dlg.wnd, win.IDCANCEL, uintptr(instance), 0)
12, 66, 75, 24, dlg.wnd, win.IDCANCEL, instance, nil)
if opts.extraButton != nil {
dlg.extraBtn, _, _ = createWindowEx.Call(0,
dlg.extraBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.extraButton),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 66, 75, 24, dlg.wnd, win.IDNO, uintptr(instance), 0)
12, 66, 75, 24, dlg.wnd, win.IDNO, instance, nil)
}
dlg.layout(getDPI(dlg.wnd))
centerWindow(dlg.wnd)
setFocus.Call(dlg.editCtl)
showWindow.Call(dlg.wnd, _SW_NORMAL, 0)
sendMessage.Call(dlg.editCtl, win.EM_SETSEL, 0, intptr(-1))
win.SetFocus(dlg.editCtl)
win.ShowWindow(dlg.wnd, _SW_NORMAL)
win.SendMessage(dlg.editCtl, win.EM_SETSEL, 0, intptr(-1))
if opts.ctx != nil {
wait := make(chan struct{})
@ -105,7 +105,7 @@ func (dlg *entryDialog) setup(text string, opts options) (string, error) {
go func() {
select {
case <-opts.ctx.Done():
sendMessage.Call(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
win.SendMessage(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
case <-wait:
}
}()
@ -122,21 +122,21 @@ func (dlg *entryDialog) setup(text string, opts options) (string, error) {
func (dlg *entryDialog) layout(dpi dpi) {
font := dlg.font.forDPI(dpi)
sendMessage.Call(dlg.textCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.editCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.okBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.cancelBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.extraBtn, win.WM_SETFONT, font, 1)
setWindowPos.Call(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(141), _SWP_NOZORDER|_SWP_NOMOVE)
setWindowPos.Call(dlg.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
setWindowPos.Call(dlg.editCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(24), _SWP_NOZORDER)
win.SendMessage(dlg.textCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.editCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.okBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.cancelBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.extraBtn, win.WM_SETFONT, font, 1)
win.SetWindowPos(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(141), _SWP_NOZORDER|_SWP_NOMOVE)
win.SetWindowPos(dlg.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
win.SetWindowPos(dlg.editCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(24), _SWP_NOZORDER)
if dlg.extraBtn == 0 {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(95), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(95), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
} else {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(12), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(12), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(66), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
}
}

View file

@ -33,7 +33,7 @@ func selectFile(opts options) (string, error) {
args.Flags = win.OFN_NOCHANGEDIR | win.OFN_FILEMUSTEXIST | win.OFN_EXPLORER
if opts.title != nil {
args.Title = syscall.StringToUTF16Ptr(*opts.title)
args.Title = strptr(*opts.title)
}
if opts.showHidden {
args.Flags |= win.OFN_FORCESHOWHIDDEN
@ -79,7 +79,7 @@ func selectFileMultiple(opts options) ([]string, error) {
args.Flags = win.OFN_NOCHANGEDIR | win.OFN_ALLOWMULTISELECT | win.OFN_FILEMUSTEXIST | win.OFN_EXPLORER
if opts.title != nil {
args.Title = syscall.StringToUTF16Ptr(*opts.title)
args.Title = strptr(*opts.title)
}
if opts.showHidden {
args.Flags |= win.OFN_FORCESHOWHIDDEN
@ -150,7 +150,7 @@ func selectFileSave(opts options) (string, error) {
args.Flags = win.OFN_NOCHANGEDIR | win.OFN_PATHMUSTEXIST | win.OFN_NOREADONLYRETURN | win.OFN_EXPLORER
if opts.title != nil {
args.Title = syscall.StringToUTF16Ptr(*opts.title)
args.Title = strptr(*opts.title)
}
if opts.confirmOverwrite {
args.Flags |= win.OFN_OVERWRITEPROMPT
@ -231,13 +231,13 @@ func pickFolders(opts options, multi bool) (str string, lst []string, err error)
}
if opts.title != nil {
ptr := syscall.StringToUTF16Ptr(*opts.title)
ptr := strptr(*opts.title)
dialog.Call(dialog.SetTitle, uintptr(unsafe.Pointer(ptr)))
}
if opts.filename != "" {
var item *win.IShellItem
ptr := syscall.StringToUTF16Ptr(opts.filename)
ptr := strptr(opts.filename)
win.SHCreateItemFromParsingName(ptr, nil, _IID_IShellItem, &item)
if int32(hr) >= 0 && item != nil {
@ -318,10 +318,10 @@ func browseForFolder(opts options) (string, []string, error) {
args.Flags = win.BIF_RETURNONLYFSDIRS
if opts.title != nil {
args.Title = syscall.StringToUTF16Ptr(*opts.title)
args.Title = strptr(*opts.title)
}
if opts.filename != "" {
args.LParam = syscall.StringToUTF16Ptr(opts.filename)
args.LParam = strptr(opts.filename)
args.CallbackFunc = syscall.NewCallback(browseForFolderCallback)
}
@ -363,10 +363,10 @@ func initDirNameExt(filename string, name []uint16) (dir *uint16, ext *uint16) {
copy(name, syscall.StringToUTF16(n))
}
if d != "" {
dir = syscall.StringToUTF16Ptr(d)
dir = strptr(d)
}
if len(e) > 1 {
ext = syscall.StringToUTF16Ptr(e[1:])
ext = strptr(e[1:])
}
return
}

View file

@ -86,6 +86,12 @@ func GetWindowThreadProcessId(hwnd HWND, pid *uint32) (tid uint32, err error) {
return windows.GetWindowThreadProcessId(hwnd, pid)
}
func SendMessagePointer(wnd HWND, msg uint32, wparam uintptr, lparam unsafe.Pointer) (ret uintptr) {
r0, _, _ := syscall.Syscall6(procSendMessageW.Addr(), 4, uintptr(wnd), uintptr(msg), uintptr(wparam), uintptr(lparam), 0, 0)
ret = uintptr(r0)
return
}
func GetDpiForWindow(wnd HWND) (ret int, err error) {
if err := procGetDpiForWindow.Find(); err != nil {
return 0, err
@ -138,7 +144,15 @@ type MSG struct {
// https://docs.microsoft.com/en-us/windows/win32/api/windef/ns-windef-point
type POINT struct {
x, y int32
X, Y int32
}
// https://docs.microsoft.com/en-us/windows/win32/api/windef/ns-windef-rect
type RECT struct {
Left int32
Top int32
Right int32
Bottom int32
}
// https://docs.microsoft.com/en-us/windows/win32/api/winuser/ns-winuser-wndclassexw
@ -157,23 +171,32 @@ type WNDCLASSEX struct {
IconSm Handle
}
//sys CreateIconFromResource(resBits []byte, icon bool, ver uint32) (ret Handle, err error) = user32.CreateIconFromResource
//sys CreateWindowEx(exStyle uint32, className *uint16, windowName *uint16, style uint32, x int, y int, width int, height int, parent HWND, menu Handle, instance Handle, param unsafe.Pointer) (ret HWND, err error) = user32.CreateWindowExW
//sys DestroyIcon(icon Handle) (err error) = user32.DestroyIcon
//sys DispatchMessage(msg *MSG) (ret uintptr) = user32.DispatchMessageW
//sys EnableWindow(wnd HWND, enable bool) (ok bool) = user32.EnableWindow
//sys EnumChildWindows(parent HWND, enumFunc uintptr, lparam unsafe.Pointer) = user32.EnumChildWindows
//sys EnumWindows(enumFunc uintptr, lparam unsafe.Pointer) (err error) = user32.EnumChildWindows
//sys GetDlgCtrlID(wnd HWND) (ret int) = user32.GetDlgCtrlID
//sys getDpiForWindow(wnd HWND) (ret int) = user32.GetDpiForWindow
//sys GetMessage(msg *MSG, wnd HWND, msgFilterMin uint32, msgFilterMax uint32) (ret uintptr) = user32.GetMessageW
//sys GetWindowDC(wnd HWND) (ret Handle) = user32.GetWindowDC
//sys GetWindowRect(wnd HWND, cmdShow *RECT) (err error) = user32.GetWindowRect
//sys GetWindowText(wnd HWND, str *uint16, maxCount int) (ret int, err error) = user32.GetWindowTextW
//sys GetWindowTextLength(wnd HWND) (ret int, err error) = user32.GetWindowTextLengthW
//sys IsDialogMessage(wnd HWND, msg *MSG) (ok bool) = user32.IsDialogMessageW
//sys LoadIcon(instance Handle, resource uintptr) (ret Handle, err error) = user32.LoadIconW
//sys LoadImage(instance Handle, name *uint16, typ int, cx int, cy int, load int) (ret Handle, err error) = user32.LoadImageW
//sys RegisterClassEx(cls *WNDCLASSEX) (ret uint16, err error) = user32.RegisterClassExW
//sys RegisterClassEx(cls *WNDCLASSEX) (err error) = user32.RegisterClassExW
//sys ReleaseDC(wnd HWND, dc Handle) (ok bool) = user32.ReleaseDC
//sys SendMessage(wnd HWND, msg uint32, wparam uintptr, lparam uintptr) (ret uintptr) = user32.SendMessageW
//sys SetFocus(wnd HWND) (ret HWND, err error) = user32.SetFocus
//sys SetForegroundWindow(wnd HWND) (ok bool) = user32.SetForegroundWindow
//sys setThreadDpiAwarenessContext(dpiContext uintptr) (ret uintptr) = user32.SetThreadDpiAwarenessContext
//sys SetWindowLong(wnd HWND, index int, newLong int) (ret int, err error) = user32.SetWindowLongW
//sys SetWindowPos(wnd HWND, wndInsertAfter HWND, x int, y int, cx int, cy int, flags int) (err error) = user32.SetWindowPos
//sys SetWindowText(wnd HWND, text *uint16) (err error) = user32.SetWindowTextW
//sys ShowWindow(wnd HWND, cmdShow int) (ok bool) = user32.ShowWindow
//sys TranslateMessage(msg *MSG) (ok bool) = user32.TranslateMessage
//sys UnregisterClass(atom uint16, instance Handle) (err error) = user32.UnregisterClassW
//sys CreateIconFromResource(resBits []byte, resSize int, icon bool, ver uint32) (ret Handle, err error) = user32.CreateIconFromResource
//sys UnregisterClass(className *uint16, instance Handle) (err error) = user32.UnregisterClassW

View file

@ -9,4 +9,6 @@ type Handle = windows.Handle
type HWND = windows.HWND
type Pointer = windows.Pointer
//sys RtlGetNtVersionNumbers(major *uint32, minor *uint32, build *uint32) = ntdll.RtlGetNtVersionNumbers
func RtlGetNtVersionNumbers() (majorVersion, minorVersion, buildNumber uint32) {
return windows.RtlGetNtVersionNumbers()
}

View file

@ -42,7 +42,6 @@ var (
modcomdlg32 = windows.NewLazySystemDLL("comdlg32.dll")
modgdi32 = windows.NewLazySystemDLL("gdi32.dll")
modkernel32 = windows.NewLazySystemDLL("kernel32.dll")
modntdll = windows.NewLazySystemDLL("ntdll.dll")
modole32 = windows.NewLazySystemDLL("ole32.dll")
modshell32 = windows.NewLazySystemDLL("shell32.dll")
moduser32 = windows.NewLazySystemDLL("user32.dll")
@ -62,29 +61,37 @@ var (
procGetConsoleWindow = modkernel32.NewProc("GetConsoleWindow")
procGetModuleHandleW = modkernel32.NewProc("GetModuleHandleW")
procReleaseActCtx = modkernel32.NewProc("ReleaseActCtx")
procRtlGetNtVersionNumbers = modntdll.NewProc("RtlGetNtVersionNumbers")
procCoCreateInstance = modole32.NewProc("CoCreateInstance")
procSHBrowseForFolder = modshell32.NewProc("SHBrowseForFolder")
procSHCreateItemFromParsingName = modshell32.NewProc("SHCreateItemFromParsingName")
procSHGetPathFromIDListEx = modshell32.NewProc("SHGetPathFromIDListEx")
procShell_NotifyIconW = modshell32.NewProc("Shell_NotifyIconW")
procCreateIconFromResource = moduser32.NewProc("CreateIconFromResource")
procCreateWindowExW = moduser32.NewProc("CreateWindowExW")
procDestroyIcon = moduser32.NewProc("DestroyIcon")
procDispatchMessageW = moduser32.NewProc("DispatchMessageW")
procEnableWindow = moduser32.NewProc("EnableWindow")
procEnumChildWindows = moduser32.NewProc("EnumChildWindows")
procGetDlgCtrlID = moduser32.NewProc("GetDlgCtrlID")
procGetDpiForWindow = moduser32.NewProc("GetDpiForWindow")
procGetMessageW = moduser32.NewProc("GetMessageW")
procGetWindowDC = moduser32.NewProc("GetWindowDC")
procGetWindowRect = moduser32.NewProc("GetWindowRect")
procGetWindowTextLengthW = moduser32.NewProc("GetWindowTextLengthW")
procGetWindowTextW = moduser32.NewProc("GetWindowTextW")
procIsDialogMessageW = moduser32.NewProc("IsDialogMessageW")
procLoadIconW = moduser32.NewProc("LoadIconW")
procLoadImageW = moduser32.NewProc("LoadImageW")
procRegisterClassExW = moduser32.NewProc("RegisterClassExW")
procReleaseDC = moduser32.NewProc("ReleaseDC")
procSendMessageW = moduser32.NewProc("SendMessageW")
procSetFocus = moduser32.NewProc("SetFocus")
procSetForegroundWindow = moduser32.NewProc("SetForegroundWindow")
procSetThreadDpiAwarenessContext = moduser32.NewProc("SetThreadDpiAwarenessContext")
procSetWindowLongW = moduser32.NewProc("SetWindowLongW")
procSetWindowPos = moduser32.NewProc("SetWindowPos")
procSetWindowTextW = moduser32.NewProc("SetWindowTextW")
procShowWindow = moduser32.NewProc("ShowWindow")
procTranslateMessage = moduser32.NewProc("TranslateMessage")
procUnregisterClassW = moduser32.NewProc("UnregisterClassW")
procWTSSendMessageW = modwtsapi32.NewProc("WTSSendMessageW")
@ -183,11 +190,6 @@ func ReleaseActCtx(actCtx Handle) {
return
}
func RtlGetNtVersionNumbers(major *uint32, minor *uint32, build *uint32) {
syscall.Syscall(procRtlGetNtVersionNumbers.Addr(), 3, uintptr(unsafe.Pointer(major)), uintptr(unsafe.Pointer(minor)), uintptr(unsafe.Pointer(build)))
return
}
func CoCreateInstance(clsid uintptr, unkOuter unsafe.Pointer, clsContext int32, iid uintptr, address unsafe.Pointer) (res error) {
r0, _, _ := syscall.Syscall6(procCoCreateInstance.Addr(), 5, uintptr(clsid), uintptr(unkOuter), uintptr(clsContext), uintptr(iid), uintptr(address), 0)
if r0 != 0 {
@ -225,7 +227,7 @@ func ShellNotifyIcon(message uint32, data *NOTIFYICONDATA) (ret int, err error)
return
}
func CreateIconFromResource(resBits []byte, resSize int, icon bool, ver uint32) (ret Handle, err error) {
func CreateIconFromResource(resBits []byte, icon bool, ver uint32) (ret Handle, err error) {
var _p0 *byte
if len(resBits) > 0 {
_p0 = &resBits[0]
@ -234,7 +236,7 @@ func CreateIconFromResource(resBits []byte, resSize int, icon bool, ver uint32)
if icon {
_p1 = 1
}
r0, _, e1 := syscall.Syscall6(procCreateIconFromResource.Addr(), 5, uintptr(unsafe.Pointer(_p0)), uintptr(len(resBits)), uintptr(resSize), uintptr(_p1), uintptr(ver), 0)
r0, _, e1 := syscall.Syscall6(procCreateIconFromResource.Addr(), 4, uintptr(unsafe.Pointer(_p0)), uintptr(len(resBits)), uintptr(_p1), uintptr(ver), 0, 0)
ret = Handle(r0)
if ret == 0 {
err = errnoErr(e1)
@ -242,6 +244,15 @@ func CreateIconFromResource(resBits []byte, resSize int, icon bool, ver uint32)
return
}
func CreateWindowEx(exStyle uint32, className *uint16, windowName *uint16, style uint32, x int, y int, width int, height int, parent HWND, menu Handle, instance Handle, param unsafe.Pointer) (ret HWND, err error) {
r0, _, e1 := syscall.Syscall12(procCreateWindowExW.Addr(), 12, uintptr(exStyle), uintptr(unsafe.Pointer(className)), uintptr(unsafe.Pointer(windowName)), uintptr(style), uintptr(x), uintptr(y), uintptr(width), uintptr(height), uintptr(parent), uintptr(menu), uintptr(instance), uintptr(param))
ret = HWND(r0)
if ret == 0 {
err = errnoErr(e1)
}
return
}
func DestroyIcon(icon Handle) (err error) {
r1, _, e1 := syscall.Syscall(procDestroyIcon.Addr(), 1, uintptr(icon), 0, 0)
if r1 == 0 {
@ -256,6 +267,16 @@ func DispatchMessage(msg *MSG) (ret uintptr) {
return
}
func EnableWindow(wnd HWND, enable bool) (ok bool) {
var _p0 uint32
if enable {
_p0 = 1
}
r0, _, _ := syscall.Syscall(procEnableWindow.Addr(), 2, uintptr(wnd), uintptr(_p0), 0)
ok = r0 != 0
return
}
func EnumWindows(enumFunc uintptr, lparam unsafe.Pointer) (err error) {
r1, _, e1 := syscall.Syscall(procEnumChildWindows.Addr(), 2, uintptr(enumFunc), uintptr(lparam), 0)
if r1 == 0 {
@ -293,6 +314,32 @@ func GetWindowDC(wnd HWND) (ret Handle) {
return
}
func GetWindowRect(wnd HWND, cmdShow *RECT) (err error) {
r1, _, e1 := syscall.Syscall(procGetWindowRect.Addr(), 2, uintptr(wnd), uintptr(unsafe.Pointer(cmdShow)), 0)
if r1 == 0 {
err = errnoErr(e1)
}
return
}
func GetWindowTextLength(wnd HWND) (ret int, err error) {
r0, _, e1 := syscall.Syscall(procGetWindowTextLengthW.Addr(), 1, uintptr(wnd), 0, 0)
ret = int(r0)
if ret == 0 {
err = errnoErr(e1)
}
return
}
func GetWindowText(wnd HWND, str *uint16, maxCount int) (ret int, err error) {
r0, _, e1 := syscall.Syscall(procGetWindowTextW.Addr(), 3, uintptr(wnd), uintptr(unsafe.Pointer(str)), uintptr(maxCount))
ret = int(r0)
if ret == 0 {
err = errnoErr(e1)
}
return
}
func IsDialogMessage(wnd HWND, msg *MSG) (ok bool) {
r0, _, _ := syscall.Syscall(procIsDialogMessageW.Addr(), 2, uintptr(wnd), uintptr(unsafe.Pointer(msg)), 0)
ok = r0 != 0
@ -317,10 +364,9 @@ func LoadImage(instance Handle, name *uint16, typ int, cx int, cy int, load int)
return
}
func RegisterClassEx(cls *WNDCLASSEX) (ret uint16, err error) {
r0, _, e1 := syscall.Syscall(procRegisterClassExW.Addr(), 1, uintptr(unsafe.Pointer(cls)), 0, 0)
ret = uint16(r0)
if ret == 0 {
func RegisterClassEx(cls *WNDCLASSEX) (err error) {
r1, _, e1 := syscall.Syscall(procRegisterClassExW.Addr(), 1, uintptr(unsafe.Pointer(cls)), 0, 0)
if r1 == 0 {
err = errnoErr(e1)
}
return
@ -338,6 +384,15 @@ func SendMessage(wnd HWND, msg uint32, wparam uintptr, lparam uintptr) (ret uint
return
}
func SetFocus(wnd HWND) (ret HWND, err error) {
r0, _, e1 := syscall.Syscall(procSetFocus.Addr(), 1, uintptr(wnd), 0, 0)
ret = HWND(r0)
if ret == 0 {
err = errnoErr(e1)
}
return
}
func SetForegroundWindow(wnd HWND) (ok bool) {
r0, _, _ := syscall.Syscall(procSetForegroundWindow.Addr(), 1, uintptr(wnd), 0, 0)
ok = r0 != 0
@ -350,6 +405,23 @@ func setThreadDpiAwarenessContext(dpiContext uintptr) (ret uintptr) {
return
}
func SetWindowLong(wnd HWND, index int, newLong int) (ret int, err error) {
r0, _, e1 := syscall.Syscall(procSetWindowLongW.Addr(), 3, uintptr(wnd), uintptr(index), uintptr(newLong))
ret = int(r0)
if ret == 0 {
err = errnoErr(e1)
}
return
}
func SetWindowPos(wnd HWND, wndInsertAfter HWND, x int, y int, cx int, cy int, flags int) (err error) {
r1, _, e1 := syscall.Syscall9(procSetWindowPos.Addr(), 7, uintptr(wnd), uintptr(wndInsertAfter), uintptr(x), uintptr(y), uintptr(cx), uintptr(cy), uintptr(flags), 0, 0)
if r1 == 0 {
err = errnoErr(e1)
}
return
}
func SetWindowText(wnd HWND, text *uint16) (err error) {
r1, _, e1 := syscall.Syscall(procSetWindowTextW.Addr(), 2, uintptr(wnd), uintptr(unsafe.Pointer(text)), 0)
if r1 == 0 {
@ -358,14 +430,20 @@ func SetWindowText(wnd HWND, text *uint16) (err error) {
return
}
func ShowWindow(wnd HWND, cmdShow int) (ok bool) {
r0, _, _ := syscall.Syscall(procShowWindow.Addr(), 2, uintptr(wnd), uintptr(cmdShow), 0)
ok = r0 != 0
return
}
func TranslateMessage(msg *MSG) (ok bool) {
r0, _, _ := syscall.Syscall(procTranslateMessage.Addr(), 1, uintptr(unsafe.Pointer(msg)), 0, 0)
ok = r0 != 0
return
}
func UnregisterClass(atom uint16, instance Handle) (err error) {
r1, _, e1 := syscall.Syscall(procUnregisterClassW.Addr(), 2, uintptr(atom), uintptr(instance), 0)
func UnregisterClass(className *uint16, instance Handle) (err error) {
r1, _, e1 := syscall.Syscall(procUnregisterClassW.Addr(), 2, uintptr(unsafe.Pointer(className)), uintptr(instance), 0)
if r1 == 0 {
err = errnoErr(e1)
}

View file

@ -43,12 +43,12 @@ type listDialog struct {
out []string
err error
wnd uintptr
textCtl uintptr
listCtl uintptr
okBtn uintptr
cancelBtn uintptr
extraBtn uintptr
wnd win.HWND
textCtl win.HWND
listCtl win.HWND
okBtn win.HWND
cancelBtn win.HWND
extraBtn win.HWND
font font
}
@ -75,49 +75,49 @@ func (dlg *listDialog) setup(text string, opts options) ([]string, error) {
defer win.UnregisterClass(cls, instance)
owner, _ := opts.attach.(win.HWND)
dlg.wnd, _, _ = createWindowEx.Call(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
uintptr(cls), strptr(*opts.title),
dlg.wnd, _ = win.CreateWindowEx(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
cls, strptr(*opts.title),
_WS_POPUPWINDOW|_WS_CLIPSIBLINGS|_WS_DLGFRAME,
_CW_USEDEFAULT, _CW_USEDEFAULT,
281, 281, uintptr(owner), 0, uintptr(instance), uintptr(unsafe.Pointer(dlg)))
281, 281, owner, 0, instance, unsafe.Pointer(dlg))
dlg.textCtl, _, _ = createWindowEx.Call(0,
dlg.textCtl, _ = win.CreateWindowEx(0,
strptr("STATIC"), strptr(text),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_SS_WORDELLIPSIS|_SS_EDITCONTROL|_SS_NOPREFIX,
12, 10, 241, 16, dlg.wnd, 0, uintptr(instance), 0)
12, 10, 241, 16, dlg.wnd, 0, instance, nil)
var flags uintptr = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _WS_VSCROLL
var flags uint32 = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _WS_VSCROLL
if dlg.multiple {
flags |= _LBS_EXTENDEDSEL
}
dlg.listCtl, _, _ = createWindowEx.Call(_WS_EX_CLIENTEDGE,
dlg.listCtl, _ = win.CreateWindowEx(_WS_EX_CLIENTEDGE,
strptr("LISTBOX"), strptr(opts.entryText),
flags,
12, 30, 241, 164, dlg.wnd, 0, uintptr(instance), 0)
12, 30, 241, 164, dlg.wnd, 0, instance, nil)
dlg.okBtn, _, _ = createWindowEx.Call(0,
dlg.okBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.okLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP|_BS_DEFPUSHBUTTON,
12, 206, 75, 24, dlg.wnd, win.IDOK, uintptr(instance), 0)
dlg.cancelBtn, _, _ = createWindowEx.Call(0,
12, 206, 75, 24, dlg.wnd, win.IDOK, instance, nil)
dlg.cancelBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.cancelLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 206, 75, 24, dlg.wnd, win.IDCANCEL, uintptr(instance), 0)
12, 206, 75, 24, dlg.wnd, win.IDCANCEL, instance, nil)
if opts.extraButton != nil {
dlg.extraBtn, _, _ = createWindowEx.Call(0,
dlg.extraBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.extraButton),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 206, 75, 24, dlg.wnd, win.IDNO, uintptr(instance), 0)
12, 206, 75, 24, dlg.wnd, win.IDNO, instance, nil)
}
for _, item := range dlg.items {
sendMessage.Call(dlg.listCtl, win.LB_ADDSTRING, 0, strptr(item))
win.SendMessagePointer(dlg.listCtl, win.LB_ADDSTRING, 0, unsafe.Pointer(strptr(item)))
}
dlg.layout(getDPI(dlg.wnd))
centerWindow(dlg.wnd)
setFocus.Call(dlg.listCtl)
showWindow.Call(dlg.wnd, _SW_NORMAL, 0)
win.SetFocus(dlg.listCtl)
win.ShowWindow(dlg.wnd, _SW_NORMAL)
if opts.ctx != nil {
wait := make(chan struct{})
@ -125,7 +125,7 @@ func (dlg *listDialog) setup(text string, opts options) ([]string, error) {
go func() {
select {
case <-opts.ctx.Done():
sendMessage.Call(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
win.SendMessage(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
case <-wait:
}
}()
@ -142,21 +142,21 @@ func (dlg *listDialog) setup(text string, opts options) ([]string, error) {
func (dlg *listDialog) layout(dpi dpi) {
font := dlg.font.forDPI(dpi)
sendMessage.Call(dlg.textCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.listCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.okBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.cancelBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.extraBtn, win.WM_SETFONT, font, 1)
setWindowPos.Call(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(281), _SWP_NOZORDER|_SWP_NOMOVE)
setWindowPos.Call(dlg.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
setWindowPos.Call(dlg.listCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(164), _SWP_NOZORDER)
win.SendMessage(dlg.textCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.listCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.okBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.cancelBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.extraBtn, win.WM_SETFONT, font, 1)
win.SetWindowPos(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(281), _SWP_NOZORDER|_SWP_NOMOVE)
win.SetWindowPos(dlg.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
win.SetWindowPos(dlg.listCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(164), _SWP_NOZORDER)
if dlg.extraBtn == 0 {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
} else {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(12), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(12), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(206), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
}
}
@ -186,18 +186,18 @@ func listProc(wnd uintptr, msg uint32, wparam uintptr, lparam *unsafe.Pointer) u
return 1
case win.IDOK, win.IDYES:
if dlg.multiple {
if len, _, _ := sendMessage.Call(dlg.listCtl, win.LB_GETSELCOUNT, 0, 0); int32(len) >= 0 {
if len := win.SendMessage(dlg.listCtl, win.LB_GETSELCOUNT, 0, 0); int32(len) >= 0 {
dlg.out = make([]string, len)
if len > 0 {
indices := make([]int32, len)
sendMessage.Call(dlg.listCtl, win.LB_GETSELITEMS, len, uintptr(unsafe.Pointer(&indices[0])))
win.SendMessage(dlg.listCtl, win.LB_GETSELITEMS, len, uintptr(unsafe.Pointer(&indices[0])))
for i, idx := range indices {
dlg.out[i] = dlg.items[idx]
}
}
}
} else {
if idx, _, _ := sendMessage.Call(dlg.listCtl, win.LB_GETCURSEL, 0, 0); int32(idx) >= 0 {
if idx := win.SendMessage(dlg.listCtl, win.LB_GETCURSEL, 0, 0); int32(idx) >= 0 {
dlg.out = []string{dlg.items[idx]}
} else {
dlg.out = []string{}

View file

@ -66,11 +66,11 @@ func message(kind messageKind, text string, opts options) error {
var title *uint16
if opts.title != nil {
title = syscall.StringToUTF16Ptr(*opts.title)
title = strptr(*opts.title)
}
owner, _ := opts.attach.(win.HWND)
s, err := win.MessageBox(owner, syscall.StringToUTF16Ptr(text), title, flags)
s, err := win.MessageBox(owner, strptr(text), title, flags)
if opts.ctx != nil && opts.ctx.Err() != nil {
return opts.ctx.Err()
@ -107,7 +107,7 @@ func hookMessageDialogCallback(wnd win.HWND, lparam *options) uintptr {
text = lparam.extraButton
}
if text != nil {
win.SetWindowText(wnd, syscall.StringToUTF16Ptr(*text))
win.SetWindowText(wnd, strptr(*text))
}
if ctl == 20 /*IDC_STATIC_OK*/ {

View file

@ -58,9 +58,7 @@ func notify(text string, opts options) error {
return err
}
var major, minor, build uint32
win.RtlGetNtVersionNumbers(&major, &minor, &build)
major, minor, _ := win.RtlGetNtVersionNumbers()
// On Windows 7 (6.1) and lower, wait up to 10 seconds to clean up.
if major < 6 || major == 6 && minor < 2 {
if opts.ctx != nil {

View file

@ -49,19 +49,19 @@ type progressDialog struct {
max int
err error
wnd uintptr
textCtl uintptr
progCtl uintptr
okBtn uintptr
cancelBtn uintptr
extraBtn uintptr
wnd win.HWND
textCtl win.HWND
progCtl win.HWND
okBtn win.HWND
cancelBtn win.HWND
extraBtn win.HWND
font font
}
func (d *progressDialog) Text(text string) error {
select {
default:
setWindowText.Call(d.textCtl, strptr(text))
win.SetWindowText(d.textCtl, strptr(text))
return nil
case <-d.done:
return d.err
@ -71,9 +71,9 @@ func (d *progressDialog) Text(text string) error {
func (d *progressDialog) Value(value int) error {
select {
default:
sendMessage.Call(d.progCtl, win.PBM_SETPOS, uintptr(value), 0)
win.SendMessage(d.progCtl, win.PBM_SETPOS, uintptr(value), 0)
if value >= d.max {
enableWindow.Call(d.okBtn, 1)
win.EnableWindow(d.okBtn, true)
}
return nil
case <-d.done:
@ -92,11 +92,11 @@ func (d *progressDialog) Done() <-chan struct{} {
func (d *progressDialog) Complete() error {
select {
default:
setWindowLong.Call(d.progCtl, intptr(_GWL_STYLE), _WS_CHILD|_WS_VISIBLE|_PBS_SMOOTH)
sendMessage.Call(d.progCtl, win.PBM_SETRANGE32, 0, 1)
sendMessage.Call(d.progCtl, win.PBM_SETPOS, 1, 0)
enableWindow.Call(d.okBtn, 1)
enableWindow.Call(d.cancelBtn, 0)
win.SetWindowLong(d.progCtl, _GWL_STYLE, _WS_CHILD|_WS_VISIBLE|_PBS_SMOOTH)
win.SendMessage(d.progCtl, win.PBM_SETRANGE32, 0, 1)
win.SendMessage(d.progCtl, win.PBM_SETPOS, 1, 0)
win.EnableWindow(d.okBtn, true)
win.EnableWindow(d.cancelBtn, false)
return nil
case <-d.done:
return d.err
@ -104,7 +104,7 @@ func (d *progressDialog) Complete() error {
}
func (d *progressDialog) Close() error {
sendMessage.Call(d.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
win.SendMessage(d.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
<-d.done
if d.err == ErrCanceled {
return nil
@ -138,50 +138,50 @@ func (dlg *progressDialog) setup(opts options) error {
defer win.UnregisterClass(cls, instance)
owner, _ := opts.attach.(win.HWND)
dlg.wnd, _, _ = createWindowEx.Call(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
uintptr(cls), strptr(*opts.title),
dlg.wnd, _ = win.CreateWindowEx(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
cls, strptr(*opts.title),
_WS_POPUPWINDOW|_WS_CLIPSIBLINGS|_WS_DLGFRAME,
_CW_USEDEFAULT, _CW_USEDEFAULT,
281, 133, uintptr(owner), 0, uintptr(instance), uintptr(unsafe.Pointer(dlg)))
281, 133, owner, 0, instance, unsafe.Pointer(dlg))
dlg.textCtl, _, _ = createWindowEx.Call(0,
strptr("STATIC"), 0,
dlg.textCtl, _ = win.CreateWindowEx(0,
strptr("STATIC"), nil,
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_SS_WORDELLIPSIS|_SS_EDITCONTROL|_SS_NOPREFIX,
12, 10, 241, 16, dlg.wnd, 0, uintptr(instance), 0)
12, 10, 241, 16, dlg.wnd, 0, instance, nil)
var flags uintptr = _WS_CHILD | _WS_VISIBLE | _PBS_SMOOTH
var flags uint32 = _WS_CHILD | _WS_VISIBLE | _PBS_SMOOTH
if opts.maxValue < 0 {
flags |= _PBS_MARQUEE
}
dlg.progCtl, _, _ = createWindowEx.Call(0,
dlg.progCtl, _ = win.CreateWindowEx(0,
strptr(_PROGRESS_CLASS),
0, flags,
12, 30, 241, 16, dlg.wnd, 0, uintptr(instance), 0)
nil, flags,
12, 30, 241, 16, dlg.wnd, 0, instance, nil)
dlg.okBtn, _, _ = createWindowEx.Call(0,
dlg.okBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.okLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP|_BS_DEFPUSHBUTTON|_WS_DISABLED,
12, 58, 75, 24, dlg.wnd, win.IDOK, uintptr(instance), 0)
12, 58, 75, 24, dlg.wnd, win.IDOK, instance, nil)
if !opts.noCancel {
dlg.cancelBtn, _, _ = createWindowEx.Call(0,
dlg.cancelBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.cancelLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 58, 75, 24, dlg.wnd, win.IDCANCEL, uintptr(instance), 0)
12, 58, 75, 24, dlg.wnd, win.IDCANCEL, instance, nil)
}
if opts.extraButton != nil {
dlg.extraBtn, _, _ = createWindowEx.Call(0,
dlg.extraBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.extraButton),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 58, 75, 24, dlg.wnd, win.IDNO, uintptr(instance), 0)
12, 58, 75, 24, dlg.wnd, win.IDNO, instance, nil)
}
dlg.layout(getDPI(dlg.wnd))
centerWindow(dlg.wnd)
showWindow.Call(dlg.wnd, _SW_NORMAL, 0)
win.ShowWindow(dlg.wnd, _SW_NORMAL)
if opts.maxValue < 0 {
sendMessage.Call(dlg.progCtl, win.PBM_SETMARQUEE, 1, 0)
win.SendMessage(dlg.progCtl, win.PBM_SETMARQUEE, 1, 0)
} else {
sendMessage.Call(dlg.progCtl, win.PBM_SETRANGE32, 0, uintptr(opts.maxValue))
win.SendMessage(dlg.progCtl, win.PBM_SETRANGE32, 0, uintptr(opts.maxValue))
}
once.Do(dlg.init.Done)
@ -191,7 +191,7 @@ func (dlg *progressDialog) setup(opts options) error {
go func() {
select {
case <-opts.ctx.Done():
sendMessage.Call(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
win.SendMessage(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
case <-wait:
}
}()
@ -208,28 +208,28 @@ func (dlg *progressDialog) setup(opts options) error {
func (d *progressDialog) layout(dpi dpi) {
font := d.font.forDPI(dpi)
sendMessage.Call(d.textCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(d.okBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(d.cancelBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(d.extraBtn, win.WM_SETFONT, font, 1)
setWindowPos.Call(d.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(133), _SWP_NOZORDER|_SWP_NOMOVE)
setWindowPos.Call(d.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
setWindowPos.Call(d.progCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
win.SendMessage(d.textCtl, win.WM_SETFONT, font, 1)
win.SendMessage(d.okBtn, win.WM_SETFONT, font, 1)
win.SendMessage(d.cancelBtn, win.WM_SETFONT, font, 1)
win.SendMessage(d.extraBtn, win.WM_SETFONT, font, 1)
win.SetWindowPos(d.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(133), _SWP_NOZORDER|_SWP_NOMOVE)
win.SetWindowPos(d.textCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
win.SetWindowPos(d.progCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
if d.extraBtn == 0 {
if d.cancelBtn == 0 {
setWindowPos.Call(d.okBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.okBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
} else {
setWindowPos.Call(d.okBtn, 0, dpi.scale(95), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(d.cancelBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.okBtn, 0, dpi.scale(95), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.cancelBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
}
} else {
if d.cancelBtn == 0 {
setWindowPos.Call(d.okBtn, 0, dpi.scale(95), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(d.extraBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.okBtn, 0, dpi.scale(95), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.extraBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
} else {
setWindowPos.Call(d.okBtn, 0, dpi.scale(12), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(d.extraBtn, 0, dpi.scale(95), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(d.cancelBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.okBtn, 0, dpi.scale(12), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.extraBtn, 0, dpi.scale(95), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(d.cancelBtn, 0, dpi.scale(178), dpi.scale(58), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
}
}
}

View file

@ -34,14 +34,14 @@ type passwordDialog struct {
pwd string
err error
wnd uintptr
uTextCtl uintptr
uEditCtl uintptr
pTextCtl uintptr
pEditCtl uintptr
okBtn uintptr
cancelBtn uintptr
extraBtn uintptr
wnd win.HWND
uTextCtl win.HWND
uEditCtl win.HWND
pTextCtl win.HWND
pEditCtl win.HWND
okBtn win.HWND
cancelBtn win.HWND
extraBtn win.HWND
font font
}
@ -68,53 +68,53 @@ func (dlg *passwordDialog) setup(opts options) (string, string, error) {
defer win.UnregisterClass(cls, instance)
owner, _ := opts.attach.(win.HWND)
dlg.wnd, _, _ = createWindowEx.Call(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
uintptr(cls), strptr(*opts.title),
dlg.wnd, _ = win.CreateWindowEx(_WS_EX_CONTROLPARENT|_WS_EX_WINDOWEDGE|_WS_EX_DLGMODALFRAME,
cls, strptr(*opts.title),
_WS_POPUPWINDOW|_WS_CLIPSIBLINGS|_WS_DLGFRAME,
_CW_USEDEFAULT, _CW_USEDEFAULT,
281, 191, uintptr(owner), 0, uintptr(instance), uintptr(unsafe.Pointer(dlg)))
281, 191, owner, 0, instance, unsafe.Pointer(dlg))
dlg.uTextCtl, _, _ = createWindowEx.Call(0,
dlg.uTextCtl, _ = win.CreateWindowEx(0,
strptr("STATIC"), strptr("Username:"),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_SS_WORDELLIPSIS|_SS_EDITCONTROL|_SS_NOPREFIX,
12, 10, 241, 16, dlg.wnd, 0, uintptr(instance), 0)
12, 10, 241, 16, dlg.wnd, 0, instance, nil)
var flags uintptr = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _ES_AUTOHSCROLL
dlg.uEditCtl, _, _ = createWindowEx.Call(_WS_EX_CLIENTEDGE,
strptr("EDIT"), 0,
var flags uint32 = _WS_CHILD | _WS_VISIBLE | _WS_GROUP | _WS_TABSTOP | _ES_AUTOHSCROLL
dlg.uEditCtl, _ = win.CreateWindowEx(_WS_EX_CLIENTEDGE,
strptr("EDIT"), nil,
flags,
12, 30, 241, 24, dlg.wnd, 0, uintptr(instance), 0)
12, 30, 241, 24, dlg.wnd, 0, instance, nil)
dlg.pTextCtl, _, _ = createWindowEx.Call(0,
dlg.pTextCtl, _ = win.CreateWindowEx(0,
strptr("STATIC"), strptr("Password:"),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_SS_WORDELLIPSIS|_SS_EDITCONTROL|_SS_NOPREFIX,
12, 60, 241, 16, dlg.wnd, 0, uintptr(instance), 0)
12, 60, 241, 16, dlg.wnd, 0, instance, nil)
dlg.pEditCtl, _, _ = createWindowEx.Call(_WS_EX_CLIENTEDGE,
strptr("EDIT"), 0,
dlg.pEditCtl, _ = win.CreateWindowEx(_WS_EX_CLIENTEDGE,
strptr("EDIT"), nil,
flags|_ES_PASSWORD,
12, 80, 241, 24, dlg.wnd, 0, uintptr(instance), 0)
12, 80, 241, 24, dlg.wnd, 0, instance, nil)
dlg.okBtn, _, _ = createWindowEx.Call(0,
dlg.okBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.okLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP|_BS_DEFPUSHBUTTON,
12, 116, 75, 24, dlg.wnd, win.IDOK, uintptr(instance), 0)
dlg.cancelBtn, _, _ = createWindowEx.Call(0,
12, 116, 75, 24, dlg.wnd, win.IDOK, instance, nil)
dlg.cancelBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.cancelLabel),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 116, 75, 24, dlg.wnd, win.IDCANCEL, uintptr(instance), 0)
12, 116, 75, 24, dlg.wnd, win.IDCANCEL, instance, nil)
if opts.extraButton != nil {
dlg.extraBtn, _, _ = createWindowEx.Call(0,
dlg.extraBtn, _ = win.CreateWindowEx(0,
strptr("BUTTON"), strptr(*opts.extraButton),
_WS_CHILD|_WS_VISIBLE|_WS_GROUP|_WS_TABSTOP,
12, 116, 75, 24, dlg.wnd, win.IDNO, uintptr(instance), 0)
12, 116, 75, 24, dlg.wnd, win.IDNO, instance, nil)
}
dlg.layout(getDPI(dlg.wnd))
centerWindow(dlg.wnd)
setFocus.Call(dlg.uEditCtl)
showWindow.Call(dlg.wnd, _SW_NORMAL, 0)
sendMessage.Call(dlg.uEditCtl, win.EM_SETSEL, 0, intptr(-1))
win.SetFocus(dlg.uEditCtl)
win.ShowWindow(dlg.wnd, _SW_NORMAL)
win.SendMessage(dlg.uEditCtl, win.EM_SETSEL, 0, intptr(-1))
if opts.ctx != nil {
wait := make(chan struct{})
@ -122,7 +122,7 @@ func (dlg *passwordDialog) setup(opts options) (string, string, error) {
go func() {
select {
case <-opts.ctx.Done():
sendMessage.Call(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
win.SendMessage(dlg.wnd, win.WM_SYSCOMMAND, _SC_CLOSE, 0)
case <-wait:
}
}()
@ -139,25 +139,25 @@ func (dlg *passwordDialog) setup(opts options) (string, string, error) {
func (dlg *passwordDialog) layout(dpi dpi) {
font := dlg.font.forDPI(dpi)
sendMessage.Call(dlg.uTextCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.uEditCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.pTextCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.pEditCtl, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.okBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.cancelBtn, win.WM_SETFONT, font, 1)
sendMessage.Call(dlg.extraBtn, win.WM_SETFONT, font, 1)
setWindowPos.Call(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(191), _SWP_NOZORDER|_SWP_NOMOVE)
setWindowPos.Call(dlg.uTextCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
setWindowPos.Call(dlg.uEditCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.pTextCtl, 0, dpi.scale(12), dpi.scale(60), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
setWindowPos.Call(dlg.pEditCtl, 0, dpi.scale(12), dpi.scale(80), dpi.scale(241), dpi.scale(24), _SWP_NOZORDER)
win.SendMessage(dlg.uTextCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.uEditCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.pTextCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.pEditCtl, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.okBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.cancelBtn, win.WM_SETFONT, font, 1)
win.SendMessage(dlg.extraBtn, win.WM_SETFONT, font, 1)
win.SetWindowPos(dlg.wnd, 0, 0, 0, dpi.scale(281), dpi.scale(191), _SWP_NOZORDER|_SWP_NOMOVE)
win.SetWindowPos(dlg.uTextCtl, 0, dpi.scale(12), dpi.scale(10), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
win.SetWindowPos(dlg.uEditCtl, 0, dpi.scale(12), dpi.scale(30), dpi.scale(241), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.pTextCtl, 0, dpi.scale(12), dpi.scale(60), dpi.scale(241), dpi.scale(16), _SWP_NOZORDER)
win.SetWindowPos(dlg.pEditCtl, 0, dpi.scale(12), dpi.scale(80), dpi.scale(241), dpi.scale(24), _SWP_NOZORDER)
if dlg.extraBtn == 0 {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(95), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(95), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
} else {
setWindowPos.Call(dlg.okBtn, 0, dpi.scale(12), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
setWindowPos.Call(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.okBtn, 0, dpi.scale(12), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.extraBtn, 0, dpi.scale(95), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
win.SetWindowPos(dlg.cancelBtn, 0, dpi.scale(178), dpi.scale(116), dpi.scale(75), dpi.scale(24), _SWP_NOZORDER)
}
}

View file

@ -20,35 +20,18 @@ var (
user32 = windows.NewLazySystemDLL("user32.dll")
callNextHookEx = user32.NewProc("CallNextHookEx")
createWindowEx = user32.NewProc("CreateWindowExW")
defWindowProc = user32.NewProc("DefWindowProcW")
destroyWindow = user32.NewProc("DestroyWindow")
enableWindow = user32.NewProc("EnableWindow")
getSystemMetrics = user32.NewProc("GetSystemMetrics")
getWindowRect = user32.NewProc("GetWindowRect")
getWindowText = user32.NewProc("GetWindowTextW")
getWindowTextLength = user32.NewProc("GetWindowTextLengthW")
postQuitMessage = user32.NewProc("PostQuitMessage")
sendMessage = user32.NewProc("SendMessageW")
setFocus = user32.NewProc("SetFocus")
setWindowLong = user32.NewProc("SetWindowLongW")
setWindowPos = user32.NewProc("SetWindowPos")
setWindowsHookEx = user32.NewProc("SetWindowsHookExW")
setWindowText = user32.NewProc("SetWindowTextW")
showWindow = user32.NewProc("ShowWindow")
systemParametersInfo = user32.NewProc("SystemParametersInfoW")
unhookWindowsHookEx = user32.NewProc("UnhookWindowsHookEx")
)
func intptr(i int64) uintptr {
return uintptr(i)
}
func strptr(s string) uintptr {
return uintptr(unsafe.Pointer(syscall.StringToUTF16Ptr(s)))
}
func hwnd(i uint64) win.HWND { return win.HWND(uintptr(i)) }
func intptr(i int64) uintptr { return uintptr(i) }
func strptr(s string) *uint16 { return syscall.StringToUTF16Ptr(s) }
func hwnd(i uint64) win.HWND { return win.HWND(uintptr(i)) }
func setup() context.CancelFunc {
var wnd win.HWND
@ -161,7 +144,7 @@ func dialogHookProc(code int32, wparam uintptr, lparam *_CWPRETSTRUCT) uintptr {
}
}
if hook.title != nil {
win.SetWindowText(lparam.Wnd, syscall.StringToUTF16Ptr(*hook.title))
win.SetWindowText(lparam.Wnd, strptr(*hook.title))
}
if hook.init != nil {
hook.init(lparam.Wnd)
@ -221,9 +204,7 @@ func deleteBackRef(id uintptr) {
type dpi int
func getDPI(_wnd uintptr) dpi {
wnd := win.HWND(_wnd)
func getDPI(wnd win.HWND) dpi {
res, _ := win.GetDpiForWindow(wnd)
if res != 0 {
return dpi(res)
@ -240,11 +221,11 @@ func getDPI(_wnd uintptr) dpi {
return dpi(res)
}
func (d dpi) scale(dim uintptr) uintptr {
func (d dpi) scale(dim int) int {
if d == 0 {
return dim
}
return dim * uintptr(d) / win.USER_DEFAULT_SCREEN_DPI
return dim * int(d) / win.USER_DEFAULT_SCREEN_DPI
}
type font struct {
@ -312,12 +293,12 @@ func getIcon(i any) icon {
switch {
case bytes.HasPrefix(data, []byte("\x00\x00\x01\x00")):
res.handle, _ = win.LoadImage(0,
syscall.StringToUTF16Ptr(path),
strptr(path),
win.IMAGE_ICON, 0, 0,
win.LR_LOADFROMFILE|win.LR_DEFAULTSIZE|win.LR_SHARED)
case bytes.HasPrefix(data, []byte("\x89PNG\r\n\x1a\n")):
res.handle, _ = win.CreateIconFromResource(
data, len(data), true, 0x00030000)
res.handle, err = win.CreateIconFromResource(
data, true, 0x00030000)
res.destroy = true
}
return res
@ -330,27 +311,27 @@ func (i *icon) delete() {
}
}
func centerWindow(wnd uintptr) {
func centerWindow(wnd win.HWND) {
getMetric := func(i uintptr) int32 {
n, _, _ := getSystemMetrics.Call(i)
return int32(n)
}
var rect _RECT
getWindowRect.Call(wnd, uintptr(unsafe.Pointer(&rect)))
x := (getMetric(0 /* SM_CXSCREEN */) - (rect.right - rect.left)) / 2
y := (getMetric(1 /* SM_CYSCREEN */) - (rect.bottom - rect.top)) / 2
setWindowPos.Call(wnd, 0, uintptr(x), uintptr(y), 0, 0, 0x5) // SWP_NOZORDER|SWP_NOSIZE
var rect win.RECT
win.GetWindowRect(wnd, &rect)
x := (getMetric(0 /* SM_CXSCREEN */) - (rect.Right - rect.Left)) / 2
y := (getMetric(1 /* SM_CYSCREEN */) - (rect.Bottom - rect.Top)) / 2
win.SetWindowPos(wnd, 0, int(x), int(y), 0, 0, 0x5) // SWP_NOZORDER|SWP_NOSIZE
}
func getWindowString(wnd uintptr) string {
len, _, _ := getWindowTextLength.Call(wnd)
func getWindowString(wnd win.HWND) string {
len, _ := win.GetWindowTextLength(wnd)
buf := make([]uint16, len+1)
getWindowText.Call(wnd, uintptr(unsafe.Pointer(&buf[0])), len+1)
win.GetWindowText(wnd, &buf[0], len+1)
return syscall.UTF16ToString(buf)
}
func registerClass(instance, icon win.Handle, proc uintptr) (uint16, error) {
func registerClass(instance, icon win.Handle, proc uintptr) (*uint16, error) {
name := "WC_" + strconv.FormatUint(uint64(proc), 16)
var wcx win.WNDCLASSEX
@ -359,9 +340,12 @@ func registerClass(instance, icon win.Handle, proc uintptr) (uint16, error) {
wcx.Icon = icon
wcx.Instance = instance
wcx.Background = 5 // COLOR_WINDOW
wcx.ClassName = syscall.StringToUTF16Ptr(name)
wcx.ClassName = strptr(name)
return win.RegisterClassEx(&wcx)
if err := win.RegisterClassEx(&wcx); err != nil {
return nil, err
}
return wcx.ClassName, nil
}
// https://stackoverflow.com/questions/4308503/how-to-enable-visual-styles-without-a-manifest
@ -374,8 +358,8 @@ func enableVisualStyles() (cookie uintptr) {
var ctx win.ACTCTX
ctx.Size = uint32(unsafe.Sizeof(ctx))
ctx.Flags = win.ACTCTX_FLAG_RESOURCE_NAME_VALID | win.ACTCTX_FLAG_SET_PROCESS_DEFAULT | win.ACTCTX_FLAG_ASSEMBLY_DIRECTORY_VALID
ctx.Source = syscall.StringToUTF16Ptr("shell32.dll")
ctx.AssemblyDirectory = syscall.StringToUTF16Ptr(dir)
ctx.Source = strptr("shell32.dll")
ctx.AssemblyDirectory = strptr(dir)
ctx.ResourceName = 124
if hnd, err := win.CreateActCtx(&ctx); err == nil {
@ -413,14 +397,6 @@ type _NONCLIENTMETRICS struct {
MessageFont win.LOGFONT
}
// https://docs.microsoft.com/en-us/windows/win32/api/windef/ns-windef-rect
type _RECT struct {
left int32
top int32
right int32
bottom int32
}
// https://docs.microsoft.com/en-us/windows/win32/api/minwinbase/ns-minwinbase-systemtime
type _SYSTEMTIME struct {
year uint16