diff --git a/lib/colorpicker.go b/lib/colorpicker.go new file mode 100644 index 0000000..fe930e2 --- /dev/null +++ b/lib/colorpicker.go @@ -0,0 +1,72 @@ +package lib + +import ( + "math" + + . "github.com/jedib0t/go-pretty/v6/text" +) + +// FIXME: REFACTOR THIS. it was written by chatty jeeps since i didnt know how to implement this + +// Accent color portal return as of xdg-desktop-portal-gnome 47.1 +type Accent struct { + Type string `json:"type"` + Data []struct { + Type string `json:"type"` + Data [3]float64 `json:"data"` + } `json:"data"` +} + +// Colors taken straight from GNOME 47 accent colors using this command: +// busctl --user call org.freedesktop.portal.Desktop /org/freedesktop/portal/desktop org.freedesktop.portal.Settings ReadOne 'ss' 'org.freedesktop.appearance' 'accent-color' +// This is as close as we can map the colors as possible afaik - Pink and Magenta DO look a like, and thats kind of a problem +var colorMap = map[Color][3]float64{ + FgHiBlack: {0, 0, 0}, + FgHiBlue: {0.207843, 0.517647, 0.894118}, + FgHiCyan: {0.129412, 0.564706, 0.643137}, + FgHiGreen: {0.227451, 0.580392, 0.290196}, + FgHiYellow: {0.784314, 0.533333, 0}, + FgHiRed: {0.901961, 0.176471, 0.258824}, + FgHiMagenta: {0.568627, 0.254902, 0.67451}, + FgHiWhite: {0.435294, 0.513726, 0.588235}, +} + +// Calculates the Euclidean distance between two colors +func colorDistance(c1, c2 [3]float64) float64 { + return math.Sqrt( + math.Pow(c1[0]-c2[0], 2) + + math.Pow(c1[1]-c2[1], 2) + + math.Pow(c1[2]-c2[2], 2), + ) +} + +func findClosestColor(rgb [3]float64) (Color, Color) { + var closestColor Color + minDistance := math.MaxFloat64 + + for color, predefinedRGB := range colorMap { + distance := colorDistance(rgb, predefinedRGB) + if distance < minDistance { + minDistance = distance + closestColor = color + } + } + + nonHiColor, isHiColor := hiToNonHiMap[closestColor] + if isHiColor { + return closestColor, nonHiColor + } + + return closestColor, closestColor +} + +var hiToNonHiMap = map[Color]Color{ + FgHiBlack: FgBlack, + FgHiRed: FgRed, + FgHiGreen: FgGreen, + FgHiYellow: FgYellow, + FgHiBlue: FgBlue, + FgHiMagenta: FgMagenta, + FgHiCyan: FgCyan, + FgHiWhite: FgWhite, +} diff --git a/lib/percentmanager.go b/lib/percentmanager.go index 3132f73..1aab529 100644 --- a/lib/percentmanager.go +++ b/lib/percentmanager.go @@ -1,9 +1,12 @@ package lib import ( + "encoding/json" "fmt" "log/slog" "math" + "os" + "strconv" "time" "github.com/jedib0t/go-pretty/v6/progress" @@ -32,47 +35,6 @@ var CuteColors = progress.StyleColors{ Speed: text.Colors{text.FgBlue}, } -func setColorsAccent(colors *progress.StyleColors, accent string) { - highlightColor := text.Colors{text.FgHiBlue} - lowColor := text.Colors{text.FgBlue} - - switch accent { - case "blue": - highlightColor = text.Colors{text.FgHiBlue} - lowColor = text.Colors{text.FgBlue} - case "teal": - highlightColor = text.Colors{text.FgHiCyan} - lowColor = text.Colors{text.FgCyan} - case "green": - highlightColor = text.Colors{text.FgHiGreen} - lowColor = text.Colors{text.FgGreen} - case "yellow": - highlightColor = text.Colors{text.FgHiYellow} - lowColor = text.Colors{text.FgYellow} - case "orange": - highlightColor = text.Colors{text.FgHiYellow} - lowColor = text.Colors{text.FgYellow} - case "red": - highlightColor = text.Colors{text.FgHiRed} - lowColor = text.Colors{text.FgRed} - case "pink": - highlightColor = text.Colors{text.FgHiMagenta} - lowColor = text.Colors{text.FgMagenta} - case "purple": - highlightColor = text.Colors{text.FgHiMagenta} - lowColor = text.Colors{text.FgMagenta} - case "slate": - highlightColor = text.Colors{text.FgHiWhite} - lowColor = text.Colors{text.FgWhite} - } - - colors.Percent = highlightColor - colors.Tracker = highlightColor - colors.Time = lowColor - colors.Value = lowColor - colors.Speed = lowColor -} - func NewProgressWriter() progress.Writer { pw := progress.NewWriter() @@ -89,6 +51,7 @@ func NewProgressWriter() progress.Writer { pw.Style().Options.PercentFormat = "%4.1f%%" colorsSet := CuteColors + pw.Style().Colors = colorsSet var targetUser int baseUser, exists := os.LookupEnv("SUDO_UID") @@ -104,12 +67,27 @@ func NewProgressWriter() progress.Writer { } if targetUser != 0 { - cli := []string{"gsettings", "get", "org.gnome.desktop.interface", "accent-color"} + cli := []string{"busctl", "--user", "--json=short", "call", "org.freedesktop.portal.Desktop", "/org/freedesktop/portal/desktop", "org.freedesktop.portal.Settings", "ReadOne", "ss", "org.freedesktop.appearance", "accent-color"} out, err := RunUID(targetUser, cli, nil) - accent := strings.TrimSpace(strings.ReplaceAll(string(out), "'", "")) - if err == nil { - setColorsAccent(&colorsSet, accent) + var accent Accent + err = json.Unmarshal(out, &accent) + if err != nil { + pw.Style().Colors = colorsSet + return pw } + + raw_color := accent.Data[0].Data + + highlightColor, lowColor := findClosestColor(raw_color) + + validHighlightColor := text.Colors{highlightColor} + validLowColor := text.Colors{lowColor} + + colorsSet.Percent = validHighlightColor + colorsSet.Tracker = validHighlightColor + colorsSet.Time = validLowColor + colorsSet.Value = validLowColor + colorsSet.Speed = validLowColor } pw.Style().Colors = colorsSet return pw