-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathhelper.go
140 lines (124 loc) · 4.44 KB
/
helper.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
130
131
132
133
134
135
136
137
138
139
140
package blink1
import (
"errors"
"fmt"
"image/color"
"strings"
"time"
hid "github.com/b1ug/gid"
)
// methods in this file serve as public helper functions
// Preload triggers the initialization of the parsers and color names.
// It's optional to call this function, and it's safe to call it multiple times.
// Currently there is no noticeable performance gain from calling this function before using other APIs.
func Preload() {
regexOnce.Do(initRegex)
}
// IsRunningOnSupportedOS returns true if the current OS is supported by underlying HID library.
func IsRunningOnSupportedOS() bool {
return hid.Supported()
}
// IsBlink1Device returns true if the device info is about a blink(1) device.
func IsBlink1Device(di *hid.DeviceInfo) bool {
if di == nil {
return false
}
if di.VendorID == b1VendorID && di.ProductID == b1ProductID {
return true
}
return false
}
// NewLightState returns a new LightState with the given color and fade time.
func NewLightState(cl color.Color, fadeTime time.Duration, ledN LEDIndex) LightState {
return LightState{
Color: cl,
LED: ledN,
FadeTime: fadeTime,
}
}
// NewLightStateRGB returns a new LightState with the given RGB color and fade time.
func NewLightStateRGB(r, g, b uint8, fadeTime time.Duration, ledN LEDIndex) LightState {
return LightState{
Color: convRGBToColor(r, g, b),
LED: ledN,
FadeTime: fadeTime,
}
}
// NewLightStateHSB returns a new LightState with the given HSB/HSV color and fade time.
// Valid hue range is [0, 360], saturation range and brightness/value range is [0, 100].
func NewLightStateHSB(h, s, b float64, fadeTime time.Duration, ledN LEDIndex) LightState {
return LightState{
Color: convHSBToColor(h, s, b),
LED: ledN,
FadeTime: fadeTime,
}
}
// HSBToRGB converts HSB to 8-bit RGB values.
// e.g. 0, 100, 100 -> 0xff, 0x00, 0x00
// The hue is in degrees [0, 360], saturation and brightness/value are percent in the range [0, 100].
// Values outside of these ranges will be clamped.
func HSBToRGB(hue, sat, bright float64) (red, green, blue uint8) {
return convHSBToRGB(hue, sat, bright)
}
// ColorToHex converts color.Color to hex string with leading #.
// e.g. color.RGBA{R: 0xff, G: 0x00, B: 0x00, A: 0xff} -> "#FF0000"
// However, if you need color names instead of hex strings, use GetNameByColor()/GetNameOrHexByColor() methods instead.
func ColorToHex(cl color.Color) string {
return convColorToHex(cl)
}
// HexToColor converts hex string to color.Color. The hex string can be in the format of #RRGGBB or #RGB or RRGGBB or RGB (case insensitive).
// e.g. "#FF0000" -> color.RGBA{R: 0xff, G: 0x00, B: 0x00, A: 0xff}
// However, if you want to convert color names to color.Color, use GetColorByName() instead.
// And if your input string is more complex and diverse than hex or names, use ParseColor() instead.
func HexToColor(hex string) (color.Color, error) {
if len(hex) < 3 {
return nil, errors.New("invalid hex: too short")
}
// remove leading #
if strings.HasPrefix(hex, "#") {
hex = hex[1:]
}
// parse
var r, g, b uint8
switch len(hex) {
case 3:
n, err := fmt.Sscanf(hex, "%1X%1X%1X", &r, &g, &b)
if err != nil || n != 3 {
return nil, fmt.Errorf("invalid #RGB hex: %s - %w", hex, err)
}
return color.RGBA{R: r * 0x11, G: g * 0x11, B: b * 0x11, A: 0xff}, nil
case 6:
n, err := fmt.Sscanf(hex, "%02X%02X%02X", &r, &g, &b)
if err != nil || n != 3 {
return nil, fmt.Errorf("invalid #RRGGBB hex: %s - %w", hex, err)
}
return color.RGBA{R: r, G: g, B: b, A: 0xff}, nil
default:
return nil, fmt.Errorf("invalid hex format: %s", hex)
}
}
// RGBToColor converts 8-bit RGB values to color.Color.
// e.g. 0xff, 0x00, 0x00 -> color.RGBA{R: 0xff, G: 0x00, B: 0x00, A: 0xff}
func RGBToColor(r, g, b uint8) color.Color {
return convRGBToColor(r, g, b)
}
// ColorToRGB converts color.Color to 8-bit RGB values.
// e.g. color.RGBA{R: 0xff, G: 0x00, B: 0x00, A: 0xff} -> 0xff, 0x00, 0x00
func ColorToRGB(cl color.Color) (r, g, b uint8) {
return convColorToRGB(cl)
}
// HexToRGB converts hex string to 8-bit RGB values. The underlying implementation is HexToColor() + ColorToRGB().
// e.g. "#FF0000" -> 0xff, 0x00, 0x00
func HexToRGB(hex string) (r, g, b uint8, err error) {
cl, err := HexToColor(hex)
if err != nil {
return
}
r, g, b = convColorToRGB(cl)
return
}
// RGBToHex converts 8-bit RGB values to hex string with leading #.
// e.g. 0xff, 0x00, 0x00 -> "#FF0000"
func RGBToHex(r, g, b uint8) string {
return fmt.Sprintf("#%02X%02X%02X", r, g, b)
}