104 lines
2.9 KiB
Go
104 lines
2.9 KiB
Go
|
// Copyright 2012 The Walk Authors. All rights reserved.
|
||
|
// Use of this source code is governed by a BSD-style
|
||
|
// license that can be found in the LICENSE file.
|
||
|
|
||
|
// +build windows
|
||
|
|
||
|
package walk
|
||
|
|
||
|
import (
|
||
|
"unsafe"
|
||
|
)
|
||
|
|
||
|
import (
|
||
|
"github.com/lxn/win"
|
||
|
"syscall"
|
||
|
)
|
||
|
|
||
|
type ProgressIndicator struct {
|
||
|
hwnd win.HWND
|
||
|
taskbarList3 *win.ITaskbarList3
|
||
|
completed uint32
|
||
|
total uint32
|
||
|
state PIState
|
||
|
overlayIcon *Icon
|
||
|
overlayIconDescription string
|
||
|
}
|
||
|
|
||
|
type PIState int
|
||
|
|
||
|
const (
|
||
|
PINoProgress PIState = win.TBPF_NOPROGRESS
|
||
|
PIIndeterminate PIState = win.TBPF_INDETERMINATE
|
||
|
PINormal PIState = win.TBPF_NORMAL
|
||
|
PIError PIState = win.TBPF_ERROR
|
||
|
PIPaused PIState = win.TBPF_PAUSED
|
||
|
)
|
||
|
|
||
|
//newTaskbarList3 precondition: Windows version is at least 6.1 (yes, Win 7 is version 6.1).
|
||
|
func newTaskbarList3(hwnd win.HWND) (*ProgressIndicator, error) {
|
||
|
var classFactoryPtr unsafe.Pointer
|
||
|
if hr := win.CoGetClassObject(&win.CLSID_TaskbarList, win.CLSCTX_ALL, nil, &win.IID_IClassFactory, &classFactoryPtr); win.FAILED(hr) {
|
||
|
return nil, errorFromHRESULT("CoGetClassObject", hr)
|
||
|
}
|
||
|
|
||
|
var taskbarList3ObjectPtr unsafe.Pointer
|
||
|
classFactory := (*win.IClassFactory)(classFactoryPtr)
|
||
|
defer classFactory.Release()
|
||
|
|
||
|
if hr := classFactory.CreateInstance(nil, &win.IID_ITaskbarList3, &taskbarList3ObjectPtr); win.FAILED(hr) {
|
||
|
return nil, errorFromHRESULT("IClassFactory.CreateInstance", hr)
|
||
|
}
|
||
|
|
||
|
return &ProgressIndicator{taskbarList3: (*win.ITaskbarList3)(taskbarList3ObjectPtr), hwnd: hwnd}, nil
|
||
|
}
|
||
|
|
||
|
func (pi *ProgressIndicator) SetState(state PIState) error {
|
||
|
if hr := pi.taskbarList3.SetProgressState(pi.hwnd, (int)(state)); win.FAILED(hr) {
|
||
|
return errorFromHRESULT("ITaskbarList3.setprogressState", hr)
|
||
|
}
|
||
|
pi.state = state
|
||
|
return nil
|
||
|
}
|
||
|
|
||
|
func (pi *ProgressIndicator) State() PIState {
|
||
|
return pi.state
|
||
|
}
|
||
|
|
||
|
func (pi *ProgressIndicator) SetTotal(total uint32) {
|
||
|
pi.total = total
|
||
|
}
|
||
|
|
||
|
func (pi *ProgressIndicator) Total() uint32 {
|
||
|
return pi.total
|
||
|
}
|
||
|
|
||
|
func (pi *ProgressIndicator) SetCompleted(completed uint32) error {
|
||
|
if hr := pi.taskbarList3.SetProgressValue(pi.hwnd, completed, pi.total); win.FAILED(hr) {
|
||
|
return errorFromHRESULT("ITaskbarList3.SetProgressValue", hr)
|
||
|
}
|
||
|
pi.completed = completed
|
||
|
return nil
|
||
|
}
|
||
|
|
||
|
func (pi *ProgressIndicator) Completed() uint32 {
|
||
|
return pi.completed
|
||
|
}
|
||
|
|
||
|
func (pi *ProgressIndicator) SetOverlayIcon(icon *Icon, description string) error {
|
||
|
handle := win.HICON(0)
|
||
|
if icon != nil {
|
||
|
handle = icon.handleForDPI(int(win.GetDpiForWindow(pi.hwnd)))
|
||
|
}
|
||
|
description16, err := syscall.UTF16PtrFromString(description)
|
||
|
if err != nil {
|
||
|
description16 = &[]uint16{0}[0]
|
||
|
}
|
||
|
if hr := pi.taskbarList3.SetOverlayIcon(pi.hwnd, handle, description16); win.FAILED(hr) {
|
||
|
return errorFromHRESULT("ITaskbarList3.SetOverlayIcon", hr)
|
||
|
}
|
||
|
pi.overlayIcon = icon
|
||
|
pi.overlayIconDescription = description
|
||
|
return nil
|
||
|
}
|