Use AppleScript for color (macos).
This commit is contained in:
parent
9668c61d8b
commit
9460254709
10 changed files with 102 additions and 107 deletions
|
@ -35,8 +35,5 @@ Why reinvent this particular wheel?
|
|||
* WSL/Cygwin/MSYS2 [support](https://github.com/ncruces/zenity/wiki/Zenity-for-WSL,-Cygwin,-MSYS2)
|
||||
* on macOS:
|
||||
* only dependency is `osascript`
|
||||
(with [JXA](https://developer.apple.com/library/archive/releasenotes/InterapplicationCommunication/RN-JavaScriptForAutomation/Articles/Introduction.html);
|
||||
`html/template` makes JavaScript easy to template)
|
||||
* on other Unixes:
|
||||
* wraps either one of `qarma`, `zenity`, `matedialog`,\
|
||||
in that order of preference
|
||||
* wraps either one of `zenity`, `qarma`, `matedialog`
|
||||
|
|
|
@ -13,7 +13,7 @@ func SelectColor(options ...Option) (color.Color, error) {
|
|||
var data zenutil.Color
|
||||
if opts.color != nil {
|
||||
r, g, b, _ := opts.color.RGBA()
|
||||
data.Color = []float32{float32(r) / 0xffff, float32(g) / 0xffff, float32(b) / 0xffff}
|
||||
data.Color = []uint32{r, g, b}
|
||||
}
|
||||
|
||||
out, err := zenutil.Run("color", data)
|
||||
|
|
|
@ -3,78 +3,77 @@
|
|||
|
||||
package zenutil
|
||||
|
||||
import "html/template"
|
||||
import "encoding/json"
|
||||
import "text/template"
|
||||
|
||||
var scripts = template.Must(template.New("").Parse(`
|
||||
{{define "color"}}<script>var app = Application.currentApplication()
|
||||
app.includeStandardAdditions = true
|
||||
app.activate()
|
||||
var opts = {}
|
||||
var scripts = template.Must(template.New("").Funcs(template.FuncMap{"json": func(v interface{}) (string, error) {
|
||||
b, err := json.Marshal(v)
|
||||
return string(b), err
|
||||
}}).Parse(`
|
||||
{{define "color" -}}tell application (path to frontmost application as text)
|
||||
activate
|
||||
{{if .Color -}}
|
||||
opts.defaultColor = {{.Color}}
|
||||
{{end -}}
|
||||
var res = app.chooseColor(opts)
|
||||
if (Array.isArray(res)) {
|
||||
res[0] = Math.round(255*res[0])
|
||||
res[1] = Math.round(255*res[1])
|
||||
res[2] = Math.round(255*res[2])
|
||||
'rgb('+res+')'
|
||||
}
|
||||
</script>{{end}}
|
||||
{{define "file"}}<script>var app = Application.currentApplication()
|
||||
set c to choose color default color { {{index .Color 0}}, {{index .Color 1}}, {{index .Color 2}} }
|
||||
{{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 & ")"
|
||||
end tell
|
||||
{{- end}}
|
||||
{{define "file" -}}var app = Application.currentApplication()
|
||||
app.includeStandardAdditions = true
|
||||
app.activate()
|
||||
var opts = {}
|
||||
{{if .Prompt -}}
|
||||
opts.withPrompt = {{.Prompt}}
|
||||
opts.withPrompt = {{json .Prompt}}
|
||||
{{end -}}
|
||||
{{if .Type -}}
|
||||
opts.ofType = {{.Type}}
|
||||
opts.ofType = {{json .Type}}
|
||||
{{end -}}
|
||||
{{if .Name -}}
|
||||
opts.defaultName = {{.Name}}
|
||||
opts.defaultName = {{json .Name}}
|
||||
{{end -}}
|
||||
{{if .Location -}}
|
||||
opts.defaultLocation = {{.Location}}
|
||||
opts.defaultLocation = {{json .Location}}
|
||||
{{end -}}
|
||||
{{if .Invisibles -}}
|
||||
opts.invisibles = {{.Invisibles}}
|
||||
opts.invisibles = {{json .Invisibles}}
|
||||
{{end -}}
|
||||
{{if .Multiple -}}
|
||||
opts.multipleSelectionsAllowed = {{.Multiple}}
|
||||
opts.multipleSelectionsAllowed = {{json .Multiple}}
|
||||
{{end -}}
|
||||
var res = app[{{.Operation}}](opts)
|
||||
var res = app[{{json .Operation}}](opts)
|
||||
if (Array.isArray(res)) {
|
||||
res.join({{.Separator}})
|
||||
res.join({{json .Separator}})
|
||||
} else {
|
||||
res.toString()
|
||||
}
|
||||
</script>{{end}}
|
||||
{{define "msg"}}<script>var app = Application.currentApplication()
|
||||
{{- end}}
|
||||
{{define "msg" -}}var app = Application.currentApplication()
|
||||
app.includeStandardAdditions = true
|
||||
app.activate()
|
||||
var opts = {}
|
||||
{{if .Message -}}
|
||||
opts.message = {{.Message}}
|
||||
opts.message = {{json .Message}}
|
||||
{{end -}}
|
||||
{{if .As -}}
|
||||
opts.as = {{.As}}
|
||||
opts.as = {{json .As}}
|
||||
{{end -}}
|
||||
{{if .Title -}}
|
||||
opts.withTitle = {{.Title}}
|
||||
opts.withTitle = {{json .Title}}
|
||||
{{end -}}
|
||||
{{if .Icon -}}
|
||||
opts.withIcon = {{.Icon}}
|
||||
opts.withIcon = {{json .Icon}}
|
||||
{{end -}}
|
||||
{{if .Buttons -}}
|
||||
opts.buttons = {{.Buttons}}
|
||||
opts.buttons = {{json .Buttons}}
|
||||
{{end -}}
|
||||
{{if .Default -}}
|
||||
opts.defaultButton = {{.Default}}
|
||||
opts.defaultButton = {{json .Default}}
|
||||
{{end -}}
|
||||
{{if .Cancel -}}
|
||||
opts.cancelButton = {{.Cancel}}
|
||||
opts.cancelButton = {{json .Cancel}}
|
||||
{{end -}}
|
||||
var res = app[{{.Operation}}]({{.Text}}, opts).buttonReturned
|
||||
res === {{.Extra}} ? res : void 0
|
||||
</script>{{end}}`))
|
||||
var res = app[{{json .Operation}}]({{json .Text}}, opts).buttonReturned
|
||||
res === {{json .Extra}} ? res : void 0
|
||||
{{- end}}`))
|
||||
|
|
|
@ -27,7 +27,7 @@ func main() {
|
|||
|
||||
str.WriteString("\n" + `{{define "`)
|
||||
str.WriteString(strings.TrimSuffix(name, filepath.Ext(name)))
|
||||
str.WriteString(`"}}<script>`)
|
||||
str.WriteString(`" -}}`)
|
||||
|
||||
func() {
|
||||
in, err := os.Open(filepath.Join(dir, name))
|
||||
|
@ -49,7 +49,7 @@ func main() {
|
|||
}
|
||||
}()
|
||||
|
||||
str.WriteString("</script>{{end}}")
|
||||
str.WriteString("{{- end}}")
|
||||
}
|
||||
|
||||
out, err := os.Create("osa_generated.go")
|
||||
|
@ -73,7 +73,11 @@ var generator = template.Must(template.New("").Parse(`// Code generated by zenit
|
|||
|
||||
package zenutil
|
||||
|
||||
import "html/template"
|
||||
import "encoding/json"
|
||||
import "text/template"
|
||||
|
||||
var scripts = template.Must(template.New("").Parse(` + "`{{.}}`" + `))
|
||||
var scripts = template.Must(template.New("").Funcs(template.FuncMap{"json": func(v interface{}) (string, error) {
|
||||
b, err := json.Marshal(v)
|
||||
return string(b), err
|
||||
}}).Parse(` + "`{{.}}`" + `))
|
||||
`))
|
||||
|
|
9
internal/zenutil/osascripts/color.applescript
Normal file
9
internal/zenutil/osascripts/color.applescript
Normal file
|
@ -0,0 +1,9 @@
|
|||
tell application (path to frontmost application as text)
|
||||
activate
|
||||
{{if .Color -}}
|
||||
set c to choose color default color { {{index .Color 0}}, {{index .Color 1}}, {{index .Color 2}} }
|
||||
{{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 & ")"
|
||||
end tell
|
|
@ -1,17 +0,0 @@
|
|||
var app = Application.currentApplication()
|
||||
app.includeStandardAdditions = true
|
||||
app.activate()
|
||||
|
||||
var opts = {}
|
||||
|
||||
{{if .Color -}}
|
||||
opts.defaultColor = {{.Color}}
|
||||
{{end -}}
|
||||
|
||||
var res = app.chooseColor(opts)
|
||||
if (Array.isArray(res)) {
|
||||
res[0] = Math.round(255*res[0])
|
||||
res[1] = Math.round(255*res[1])
|
||||
res[2] = Math.round(255*res[2])
|
||||
'rgb('+res+')'
|
||||
}
|
|
@ -5,27 +5,27 @@ app.activate()
|
|||
var opts = {}
|
||||
|
||||
{{if .Prompt -}}
|
||||
opts.withPrompt = {{.Prompt}}
|
||||
opts.withPrompt = {{json .Prompt}}
|
||||
{{end -}}
|
||||
{{if .Type -}}
|
||||
opts.ofType = {{.Type}}
|
||||
opts.ofType = {{json .Type}}
|
||||
{{end -}}
|
||||
{{if .Name -}}
|
||||
opts.defaultName = {{.Name}}
|
||||
opts.defaultName = {{json .Name}}
|
||||
{{end -}}
|
||||
{{if .Location -}}
|
||||
opts.defaultLocation = {{.Location}}
|
||||
opts.defaultLocation = {{json .Location}}
|
||||
{{end -}}
|
||||
{{if .Invisibles -}}
|
||||
opts.invisibles = {{.Invisibles}}
|
||||
opts.invisibles = {{json .Invisibles}}
|
||||
{{end -}}
|
||||
{{if .Multiple -}}
|
||||
opts.multipleSelectionsAllowed = {{.Multiple}}
|
||||
opts.multipleSelectionsAllowed = {{json .Multiple}}
|
||||
{{end -}}
|
||||
|
||||
var res = app[{{.Operation}}](opts)
|
||||
var res = app[{{json .Operation}}](opts)
|
||||
if (Array.isArray(res)) {
|
||||
res.join({{.Separator}})
|
||||
res.join({{json .Separator}})
|
||||
} else {
|
||||
res.toString()
|
||||
}
|
|
@ -1,30 +0,0 @@
|
|||
var app = Application.currentApplication()
|
||||
app.includeStandardAdditions = true
|
||||
app.activate()
|
||||
|
||||
var opts = {}
|
||||
|
||||
{{if .Message -}}
|
||||
opts.message = {{.Message}}
|
||||
{{end -}}
|
||||
{{if .As -}}
|
||||
opts.as = {{.As}}
|
||||
{{end -}}
|
||||
{{if .Title -}}
|
||||
opts.withTitle = {{.Title}}
|
||||
{{end -}}
|
||||
{{if .Icon -}}
|
||||
opts.withIcon = {{.Icon}}
|
||||
{{end -}}
|
||||
{{if .Buttons -}}
|
||||
opts.buttons = {{.Buttons}}
|
||||
{{end -}}
|
||||
{{if .Default -}}
|
||||
opts.defaultButton = {{.Default}}
|
||||
{{end -}}
|
||||
{{if .Cancel -}}
|
||||
opts.cancelButton = {{.Cancel}}
|
||||
{{end -}}
|
||||
|
||||
var res = app[{{.Operation}}]({{.Text}}, opts).buttonReturned
|
||||
res === {{.Extra}} ? res : void 0
|
30
internal/zenutil/osascripts/msg.js
Normal file
30
internal/zenutil/osascripts/msg.js
Normal file
|
@ -0,0 +1,30 @@
|
|||
var app = Application.currentApplication()
|
||||
app.includeStandardAdditions = true
|
||||
app.activate()
|
||||
|
||||
var opts = {}
|
||||
|
||||
{{if .Message -}}
|
||||
opts.message = {{json .Message}}
|
||||
{{end -}}
|
||||
{{if .As -}}
|
||||
opts.as = {{json .As}}
|
||||
{{end -}}
|
||||
{{if .Title -}}
|
||||
opts.withTitle = {{json .Title}}
|
||||
{{end -}}
|
||||
{{if .Icon -}}
|
||||
opts.withIcon = {{json .Icon}}
|
||||
{{end -}}
|
||||
{{if .Buttons -}}
|
||||
opts.buttons = {{json .Buttons}}
|
||||
{{end -}}
|
||||
{{if .Default -}}
|
||||
opts.defaultButton = {{json .Default}}
|
||||
{{end -}}
|
||||
{{if .Cancel -}}
|
||||
opts.cancelButton = {{json .Cancel}}
|
||||
{{end -}}
|
||||
|
||||
var res = app[{{json .Operation}}]({{json .Text}}, opts).buttonReturned
|
||||
res === {{json .Extra}} ? res : void 0
|
|
@ -15,19 +15,22 @@ func Run(script string, data interface{}) ([]byte, error) {
|
|||
return nil, err
|
||||
}
|
||||
|
||||
res := buf.String()
|
||||
res = res[len("<script>") : len(res)-len("\n</script>")]
|
||||
script = buf.String()
|
||||
lang := "AppleScript"
|
||||
if strings.HasPrefix(script, "var app") {
|
||||
lang = "JavaScript"
|
||||
}
|
||||
|
||||
if Command {
|
||||
path, err := exec.LookPath("osascript")
|
||||
if err == nil {
|
||||
os.Stderr.Close()
|
||||
syscall.Exec(path, []string{"osascript", "-l", "JavaScript", "-e", res}, nil)
|
||||
syscall.Exec(path, []string{"osascript", "-l", lang, "-e", script}, nil)
|
||||
}
|
||||
}
|
||||
|
||||
cmd := exec.Command("osascript", "-l", "JavaScript")
|
||||
cmd.Stdin = strings.NewReader(res)
|
||||
cmd := exec.Command("osascript", "-l", lang)
|
||||
cmd.Stdin = strings.NewReader(script)
|
||||
return cmd.Output()
|
||||
}
|
||||
|
||||
|
@ -43,7 +46,7 @@ type File struct {
|
|||
}
|
||||
|
||||
type Color struct {
|
||||
Color []float32
|
||||
Color []uint32
|
||||
}
|
||||
|
||||
type Msg struct {
|
||||
|
|
Loading…
Reference in a new issue