Color dialog (linux).

This commit is contained in:
Nuno Cruces 2020-01-21 16:13:45 +00:00
parent 9460254709
commit 0728bdf5ad
11 changed files with 114 additions and 17 deletions

View file

@ -11,6 +11,7 @@ Lots of things are missing.
For now, these are the only implemented dialogs:
* [message](https://github.com/ncruces/zenity/wiki/Message-dialog) (error, info, question, warning)
* [file selection](https://github.com/ncruces/zenity/wiki/File-Selection-dialog)
* [color selection](https://github.com/ncruces/zenity/wiki/Color-Selection-dialog)
Behavior on Windows, macOS and other Unixes might differ slightly.
Some of that is intended (reflecting platform differences),

View file

@ -2,6 +2,7 @@ package main
import (
"flag"
"image/color"
"os"
"os/exec"
"path/filepath"
@ -21,6 +22,7 @@ var (
warningDlg bool
questionDlg bool
fileSelectionDlg bool
colorSelectionDlg bool
// General options
title string
@ -46,6 +48,10 @@ var (
separator string
fileFilters FileFilters
// Color selection options
initColor string
palette bool
// Windows specific options
cygpath bool
wslpath bool
@ -77,6 +83,9 @@ func main() {
case multiple:
lstResult(egestPaths(zenity.SelectFileMutiple(opts...)))
}
case colorSelectionDlg:
clrResult(zenity.SelectColor(opts...))
}
flag.Usage()
@ -91,6 +100,7 @@ func setupFlags() {
flag.BoolVar(&warningDlg, "warning", false, "Display warning dialog")
flag.BoolVar(&questionDlg, "question", false, "Display question dialog")
flag.BoolVar(&fileSelectionDlg, "file-selection", false, "Display file selection dialog")
flag.BoolVar(&colorSelectionDlg, "color-selection", false, "Display color selection dialog")
// General options
@ -119,6 +129,10 @@ func setupFlags() {
flag.StringVar(&separator, "separator", "|", "Set output separator character")
flag.Var(&fileFilters, "file-filter", "Set a filename filter (NAME | PATTERN1 PATTERN2 ...)")
// Color selection options
flag.StringVar(&initColor, "color", "", "Set the color")
flag.BoolVar(&palette, "show-palette", false, "Show the palette")
// Windows specific options
if runtime.GOOS == "windows" {
flag.BoolVar(&cygpath, "cygpath", false, "Use cygpath for path translation (Windows only)")
@ -143,6 +157,9 @@ func validateFlags() {
if fileSelectionDlg {
n++
}
if colorSelectionDlg {
n++
}
if n != 1 {
flag.Usage()
os.Exit(-1)
@ -187,7 +204,9 @@ func loadFlags() []zenity.Option {
// File selection options
options = append(options, fileFilters.Build())
if filename != "" {
options = append(options, zenity.Filename(ingestPath(filename)))
}
if directory {
options = append(options, zenity.Directory())
}
@ -203,6 +222,15 @@ func loadFlags() []zenity.Option {
zenutil.Separator = separator
// Color selection options
if initColor != "" {
options = append(options, zenity.Color(zenutil.ParseColor(initColor)))
}
if palette {
options = append(options, zenity.ShowPalette())
}
return options
}
@ -251,6 +279,20 @@ func lstResult(l []string, err error) {
os.Exit(0)
}
func clrResult(c color.Color, err error) {
if err != nil {
os.Stderr.WriteString(err.Error())
os.Stderr.WriteString(zenutil.LineBreak)
os.Exit(-1)
}
if c == nil {
os.Exit(1)
}
os.Stdout.WriteString(zenutil.UnparseColor(c))
os.Stdout.WriteString(zenutil.LineBreak)
os.Exit(0)
}
func ingestPath(path string) string {
if runtime.GOOS == "windows" && path != "" {
var args []string

View file

@ -12,8 +12,8 @@ func SelectColor(options ...Option) (color.Color, error) {
var data zenutil.Color
if opts.color != nil {
r, g, b, _ := opts.color.RGBA()
data.Color = []uint32{r, g, b}
n := color.NRGBA64Model.Convert(opts.color).(color.NRGBA64)
data.Color = []uint16{n.R, n.G, n.B}
}
out, err := zenutil.Run("color", data)

View file

@ -8,13 +8,13 @@ import (
func ExampleSelectColor() {
zenity.SelectColor(
zenity.Color(color.RGBA{R: 0x66, G: 0x33, B: 0x99, A: 0xff}))
zenity.Color(color.NRGBA{R: 0x66, G: 0x33, B: 0x99, A: 0x80}))
// Output:
}
func ExampleSelectColor_palette() {
zenity.SelectColor(
zenity.ShowPalette(),
zenity.Color(color.RGBA{R: 0x66, G: 0x33, B: 0x99, A: 0xff}))
zenity.Color(color.NRGBA{R: 0x66, G: 0x33, B: 0x99, A: 0xff}))
// Output:
}

40
color_unix.go Normal file
View file

@ -0,0 +1,40 @@
// +build !windows,!darwin
package zenity
import (
"image/color"
"os/exec"
"github.com/ncruces/zenity/internal/zenutil"
)
// Display color selection dialog.
//
// Returns nil on cancel.
//
// Valid options: Title, Color, ShowPalette.
func SelectColor(options ...Option) (color.Color, error) {
opts := optsParse(options)
args := []string{"--color-selection"}
if opts.title != "" {
args = append(args, "--title", opts.title)
}
if opts.color != nil {
args = append(args, "--color", zenutil.UnparseColor(opts.color))
}
if opts.palette {
args = append(args, "--show-palette")
}
out, err := zenutil.Run(args)
if err, ok := err.(*exec.ExitError); ok && err.ExitCode() != 255 {
return nil, nil
}
if err != nil {
return nil, err
}
return zenutil.ParseColor(string(out)), nil
}

View file

@ -34,8 +34,8 @@ func SelectColor(options ...Option) (color.Color, error) {
if opts.color != nil {
args.Flags |= 0x1 // CC_RGBINIT
r, g, b, _ := opts.color.RGBA()
args.RgbResult = (r >> 8 << 0) | (g >> 8 << 8) | (b >> 8 << 16)
n := color.NRGBAModel.Convert(opts.color).(color.NRGBA)
args.RgbResult = uint32(n.R) | (uint32(n.G) << 8) | (uint32(n.B) << 16)
}
if opts.palette {
args.Flags |= 4 // CC_PREVENTFULLOPEN

View file

@ -39,6 +39,18 @@ func ParseColor(s string) color.Color {
}
}
c, _ := colornames.Map[strings.ToLower(s)]
c, ok := colornames.Map[strings.ToLower(s)]
if ok {
return c
}
return nil
}
func UnparseColor(c color.Color) string {
n := color.NRGBAModel.Convert(c).(color.NRGBA)
if n.A == 255 {
return fmt.Sprintf("rgb(%d,%d,%d)", n.R, n.G, n.B)
} else {
return fmt.Sprintf("rgba(%d,%d,%d,%f)", n.R, n.G, n.B, float32(n.A)/255)
}
}

View file

@ -17,7 +17,7 @@ set c to choose color default color { {{index .Color 0}}, {{index .Color 1}}, {{
{{else -}}
set c to choose color
{{end}}
"rgb(" & (item 1 of c) div 257 & "," & (item 2 of c) div 257 & "," & (item 3 of c) div 257 & ")"
"rgb(" & (item 1 of c) div 256 & "," & (item 2 of c) div 256 & "," & (item 3 of c) div 256 & ")"
end tell
{{- end}}
{{define "file" -}}var app = Application.currentApplication()

View file

@ -5,5 +5,5 @@ tell application (path to frontmost application as text)
{{else -}}
set c to choose color
{{end}}
"rgb(" & (item 1 of c) div 257 & "," & (item 2 of c) div 257 & "," & (item 3 of c) div 257 & ")"
"rgb(" & (item 1 of c) div 256 & "," & (item 2 of c) div 256 & "," & (item 3 of c) div 256 & ")"
end tell

View file

@ -46,7 +46,7 @@ type File struct {
}
type Color struct {
Color []uint32
Color []uint16
}
type Msg struct {

View file

@ -112,10 +112,12 @@ func (f FileFilters) Build() Option {
// Color selection options
// Option to set the color.
func Color(c color.Color) Option {
return func(o *options) { o.color = c }
}
// Option to show the palette.
func ShowPalette() Option {
return func(o *options) { o.palette = true }
}