open gocui when DISPLAY=""
Signed-off-by: Jeff Carr <jcarr@wit.com>
This commit is contained in:
parent
5ba335ddee
commit
8f6e971948
|
@ -127,13 +127,16 @@ Creates a window helpful for debugging this package
|
||||||
|
|
||||||
`func Indent(b bool, a ...interface{})`
|
`func Indent(b bool, a ...interface{})`
|
||||||
|
|
||||||
### func [InitPlugins](/main.go#L58)
|
### func [InitPlugins](/main.go#L61)
|
||||||
|
|
||||||
`func InitPlugins(names []string)`
|
`func InitPlugins(names []string) []string`
|
||||||
|
|
||||||
|
TODO: add logic to just load the 1st 'most common' gui toolkit
|
||||||
|
and allow the 'go-arg' command line args to override the defaults
|
||||||
|
|
||||||
### func [LoadToolkit](/plugin.go#L50)
|
### func [LoadToolkit](/plugin.go#L50)
|
||||||
|
|
||||||
`func LoadToolkit(name string) bool`
|
`func LoadToolkit(name string) *aplug`
|
||||||
|
|
||||||
loads and initializes a toolkit (andlabs/ui, gocui, etc)
|
loads and initializes a toolkit (andlabs/ui, gocui, etc)
|
||||||
|
|
||||||
|
@ -159,7 +162,7 @@ This should not pass a function
|
||||||
|
|
||||||
`func ShowDebugValues()`
|
`func ShowDebugValues()`
|
||||||
|
|
||||||
### func [StandardExit](/main.go#L255)
|
### func [StandardExit](/main.go#L262)
|
||||||
|
|
||||||
`func StandardExit()`
|
`func StandardExit()`
|
||||||
|
|
||||||
|
@ -248,11 +251,11 @@ func main() {
|
||||||
You get a window
|
You get a window
|
||||||
```
|
```
|
||||||
|
|
||||||
#### func [Start](/main.go#L98)
|
#### func [Start](/main.go#L97)
|
||||||
|
|
||||||
`func Start() *Node`
|
`func Start() *Node`
|
||||||
|
|
||||||
#### func [StartS](/main.go#L180)
|
#### func [StartS](/main.go#L178)
|
||||||
|
|
||||||
`func StartS(name string) *Node`
|
`func StartS(name string) *Node`
|
||||||
|
|
||||||
|
|
|
@ -11,6 +11,7 @@ import (
|
||||||
|
|
||||||
var title string = "Demo Plugin Window"
|
var title string = "Demo Plugin Window"
|
||||||
var outfile string = "/tmp/guilogfile"
|
var outfile string = "/tmp/guilogfile"
|
||||||
|
var myGui *gui.Node
|
||||||
|
|
||||||
var buttonCounter int = 5
|
var buttonCounter int = 5
|
||||||
|
|
||||||
|
@ -27,25 +28,13 @@ func main() {
|
||||||
// gui.Init()
|
// gui.Init()
|
||||||
|
|
||||||
// buttonWindow()
|
// buttonWindow()
|
||||||
go gui.Main(func () {
|
myGui = gui.Start()
|
||||||
log.Println("START Main f()")
|
time.Sleep(1 * time.Second)
|
||||||
buttonWindow()
|
buttonWindow()
|
||||||
/*
|
|
||||||
log.Println("END NewWindow()")
|
|
||||||
log.Println("START NewGroup()")
|
|
||||||
g := w.NewGroup("new Group 22")
|
|
||||||
log.Println("END NewGroup()")
|
|
||||||
g.NewButton("asdjkl", func () {
|
|
||||||
log.Println("world")
|
|
||||||
})
|
|
||||||
*/
|
|
||||||
log.Println("END Main f()")
|
|
||||||
// gui.StandardExit(nil)
|
|
||||||
})
|
|
||||||
log.Println("Main() END")
|
log.Println("Main() END")
|
||||||
time.Sleep(1 * time.Second)
|
time.Sleep(1 * time.Second)
|
||||||
gui.StartS("gocui")
|
// gui.StartS("gocui")
|
||||||
gui.Redraw("gocui")
|
// gui.Redraw("gocui")
|
||||||
gui.Watchdog()
|
gui.Watchdog()
|
||||||
gui.StandardExit()
|
gui.StandardExit()
|
||||||
}
|
}
|
||||||
|
@ -84,6 +73,10 @@ func buttonWindow() {
|
||||||
gui.Redraw("gocui")
|
gui.Redraw("gocui")
|
||||||
})
|
})
|
||||||
|
|
||||||
|
g.NewButton("Load 'andlabs'", func () {
|
||||||
|
gui.StartS("andlabs")
|
||||||
|
})
|
||||||
|
|
||||||
g.NewButton("NewButton(more)", func () {
|
g.NewButton("NewButton(more)", func () {
|
||||||
log.Println("new foobar 2. Adding button 'foobar 3'")
|
log.Println("new foobar 2. Adding button 'foobar 3'")
|
||||||
name := "foobar " + strconv.Itoa(buttonCounter)
|
name := "foobar " + strconv.Itoa(buttonCounter)
|
||||||
|
|
47
main.go
47
main.go
|
@ -1,6 +1,7 @@
|
||||||
package gui
|
package gui
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"os"
|
||||||
// "embed"
|
// "embed"
|
||||||
"git.wit.org/wit/gui/toolkit"
|
"git.wit.org/wit/gui/toolkit"
|
||||||
)
|
)
|
||||||
|
@ -55,44 +56,42 @@ func doGuiChan() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func InitPlugins(names []string) {
|
// TODO: add logic to just load the 1st 'most common' gui toolkit
|
||||||
|
// and allow the 'go-arg' command line args to override the defaults
|
||||||
|
func InitPlugins(names []string) []string {
|
||||||
log(debugGui, "Starting gui.Init()")
|
log(debugGui, "Starting gui.Init()")
|
||||||
|
|
||||||
for _, aplug := range allPlugins {
|
for _, aplug := range allPlugins {
|
||||||
log(debugGui, "LoadToolkit() already loaded toolkit plugin =", aplug.name)
|
log(debugGui, "LoadToolkit() already loaded toolkit plugin =", aplug.name)
|
||||||
for _, name := range names {
|
for _, name := range names {
|
||||||
if (name == aplug.name) {
|
if (name == aplug.name) {
|
||||||
return
|
return []string{name}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// try to load each plugin in the order passed to this function
|
// try to load each plugin in the order passed to this function
|
||||||
for _, name := range names {
|
for _, name := range names {
|
||||||
if (LoadToolkit(name)) {
|
aPlug := LoadToolkit(name)
|
||||||
// aplug.InitOk = true
|
if (aPlug != nil) {
|
||||||
// aplug.Init()
|
// exit because it worked!
|
||||||
return
|
return []string{name}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// the program didn't specify a plugin. Try to load one
|
// the program didn't specify a plugin. Try to load one
|
||||||
// TODO: detect the OS & user preferences to load the best one
|
// TODO: detect the OS & user preferences to load the best one
|
||||||
// TODO: commented out Init() on 02/26/2023 because I'm not sure how to run it correctly
|
// TODO: commented out Init() on 02/26/2023 because I'm not sure how to run it correctly
|
||||||
if (LoadToolkit("andlabs")) {
|
andlabsPlug := LoadToolkit("andlabs")
|
||||||
// aplug.InitOk = true
|
if (andlabsPlug != nil) {
|
||||||
// aplug.Init()
|
return []string{}
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (LoadToolkit("gocui")) {
|
gocuiPlug := LoadToolkit("andlabs")
|
||||||
// aplug.InitOk = true
|
if (gocuiPlug != nil) {
|
||||||
// aplug.Init()
|
return []string{}
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
return []string{}
|
||||||
// Should die here? TODO: need a Node to call StandardExit
|
|
||||||
// StandardExit("golang wit/gui could not load a plugin TODO: do something to STDOUT (?)")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func Start() *Node {
|
func Start() *Node {
|
||||||
|
@ -173,13 +172,13 @@ func (n *Node) doUserEvent(a toolkit.Action) {
|
||||||
|
|
||||||
func (n *Node) LoadPlugin(name string) bool {
|
func (n *Node) LoadPlugin(name string) bool {
|
||||||
StartS(name)
|
StartS(name)
|
||||||
Redraw(name)
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
func StartS(name string) *Node {
|
func StartS(name string) *Node {
|
||||||
log(logInfo, "Start() Main(f) for name =", name)
|
log(logInfo, "Start() Main(f) for name =", name)
|
||||||
if (LoadToolkit(name) == false) {
|
aplug := LoadToolkit(name)
|
||||||
|
if (aplug == nil) {
|
||||||
return Config.rootNode
|
return Config.rootNode
|
||||||
}
|
}
|
||||||
// will this really work on mswindows & macos?
|
// will this really work on mswindows & macos?
|
||||||
|
@ -187,6 +186,7 @@ func StartS(name string) *Node {
|
||||||
}
|
}
|
||||||
go Main(f)
|
go Main(f)
|
||||||
sleep(1) // temp hack until chan communication is setup
|
sleep(1) // temp hack until chan communication is setup
|
||||||
|
Config.rootNode.Redraw(aplug)
|
||||||
return Config.rootNode
|
return Config.rootNode
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -194,7 +194,14 @@ func StartS(name string) *Node {
|
||||||
func Main(f func()) {
|
func Main(f func()) {
|
||||||
log(debugGui, "Starting gui.Main() (using gtk via andlabs/ui)")
|
log(debugGui, "Starting gui.Main() (using gtk via andlabs/ui)")
|
||||||
|
|
||||||
InitPlugins([]string{"andlabs", "gocui"})
|
// TODO: this is linux only
|
||||||
|
// TODO: detect if this was run from the command line (parent == bash?)
|
||||||
|
// if DISPLAY is not set, don't even bother with loading andlabs
|
||||||
|
if (os.Getenv("DISPLAY") == "") {
|
||||||
|
InitPlugins([]string{"gocui"})
|
||||||
|
} else {
|
||||||
|
InitPlugins([]string{"andlabs", "gocui"})
|
||||||
|
}
|
||||||
|
|
||||||
if (Config.guiChan == nil) {
|
if (Config.guiChan == nil) {
|
||||||
Config.guiChan = make(chan toolkit.Action)
|
Config.guiChan = make(chan toolkit.Action)
|
||||||
|
|
26
plugin.go
26
plugin.go
|
@ -47,8 +47,9 @@ type aplug struct {
|
||||||
var allPlugins []*aplug
|
var allPlugins []*aplug
|
||||||
|
|
||||||
// loads and initializes a toolkit (andlabs/ui, gocui, etc)
|
// loads and initializes a toolkit (andlabs/ui, gocui, etc)
|
||||||
func LoadToolkit(name string) bool {
|
func LoadToolkit(name string) *aplug {
|
||||||
var newPlug aplug
|
var newPlug *aplug
|
||||||
|
newPlug = new(aplug)
|
||||||
|
|
||||||
log(debugGui, "gui.LoadToolkit() START")
|
log(debugGui, "gui.LoadToolkit() START")
|
||||||
newPlug.LoadOk = false
|
newPlug.LoadOk = false
|
||||||
|
@ -57,44 +58,45 @@ func LoadToolkit(name string) bool {
|
||||||
log(debugGui, "gui.LoadToolkit() already loaded toolkit plugin =", aplug.name)
|
log(debugGui, "gui.LoadToolkit() already loaded toolkit plugin =", aplug.name)
|
||||||
if (aplug.name == name) {
|
if (aplug.name == name) {
|
||||||
log(debugGui, "gui.LoadToolkit() SKIPPING")
|
log(debugGui, "gui.LoadToolkit() SKIPPING")
|
||||||
return true
|
return aplug
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// locate the shared library file
|
// locate the shared library file
|
||||||
filename := name + ".so"
|
filename := name + ".so"
|
||||||
loadPlugin(&newPlug, filename)
|
loadPlugin(newPlug, filename)
|
||||||
if (newPlug.plug == nil) {
|
if (newPlug.plug == nil) {
|
||||||
log(true, "attempt to find plugin", filename, "failed")
|
log(true, "attempt to find plugin", filename, "failed")
|
||||||
return false
|
return nil
|
||||||
}
|
}
|
||||||
// newPlug.Ok = true
|
// newPlug.Ok = true
|
||||||
newPlug.name = name
|
newPlug.name = name
|
||||||
|
|
||||||
// deprecate Init(?)
|
// deprecate Init(?)
|
||||||
newPlug.Init = loadFuncE(&newPlug, "Init")
|
newPlug.Init = loadFuncE(newPlug, "Init")
|
||||||
|
|
||||||
// should make a goroutine that never exits
|
// should make a goroutine that never exits
|
||||||
newPlug.Main = loadFuncF(&newPlug, "Main")
|
newPlug.Main = loadFuncF(newPlug, "Main")
|
||||||
|
|
||||||
// should send things to the goroutine above
|
// should send things to the goroutine above
|
||||||
// newPlug.Queue = loadFuncF(&newPlug, "Queue")
|
// newPlug.Queue = loadFuncF(&newPlug, "Queue")
|
||||||
|
|
||||||
// unload the plugin and restore state
|
// unload the plugin and restore state
|
||||||
newPlug.Quit = loadFuncE(&newPlug, "Quit")
|
newPlug.Quit = loadFuncE(newPlug, "Quit")
|
||||||
|
|
||||||
// Sends instructions like "Add", "Delete", "Disable", etc
|
// Sends instructions like "Add", "Delete", "Disable", etc
|
||||||
// Sends a widget (button, checkbox, etc) and it's parent widget
|
// Sends a widget (button, checkbox, etc) and it's parent widget
|
||||||
newPlug.Action = loadFuncA(&newPlug, "Action")
|
newPlug.Action = loadFuncA(newPlug, "Action")
|
||||||
|
|
||||||
newPlug.Callback = loadCallback(&newPlug, "Callback")
|
newPlug.Callback = loadCallback(newPlug, "Callback")
|
||||||
|
|
||||||
allPlugins = append(allPlugins, &newPlug)
|
allPlugins = append(allPlugins, newPlug)
|
||||||
|
|
||||||
log(debugPlugin, "gui.LoadToolkit() END", newPlug.name, filename)
|
log(debugPlugin, "gui.LoadToolkit() END", newPlug.name, filename)
|
||||||
newPlug.Init()
|
newPlug.Init()
|
||||||
|
Config.rootNode.Redraw(newPlug)
|
||||||
newPlug.LoadOk = true
|
newPlug.LoadOk = true
|
||||||
return true
|
return newPlug
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: All these functions need to be done a smarter way
|
// TODO: All these functions need to be done a smarter way
|
||||||
|
|
|
@ -38,9 +38,10 @@ func helplayout(g *gocui.Gui) error {
|
||||||
fmt.Fprintln(help, "d: show/hide debugging")
|
fmt.Fprintln(help, "d: show/hide debugging")
|
||||||
fmt.Fprintln(help, "h: hide widgets")
|
fmt.Fprintln(help, "h: hide widgets")
|
||||||
fmt.Fprintln(help, "s: show all widgets")
|
fmt.Fprintln(help, "s: show all widgets")
|
||||||
|
fmt.Fprintln(help, "q: quit()")
|
||||||
fmt.Fprintln(help, "p: panic()")
|
fmt.Fprintln(help, "p: panic()")
|
||||||
fmt.Fprintln(help, "STDOUT: /tmp/witgui.log")
|
fmt.Fprintln(help, "STDOUT: /tmp/witgui.log")
|
||||||
fmt.Fprintln(help, "Ctrl-C or Q: Exit")
|
// fmt.Fprintln(help, "Ctrl-C: Exit") // TODO: fix ctrl-c handling
|
||||||
if _, err := g.SetCurrentView("help"); err != nil {
|
if _, err := g.SetCurrentView("help"); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
|
@ -70,9 +70,24 @@ func addDebugKeys(g *gocui.Gui) {
|
||||||
return nil
|
return nil
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// exit
|
||||||
|
g.SetKeybinding("", 'q', gocui.ModNone,
|
||||||
|
func(g *gocui.Gui, v *gocui.View) error {
|
||||||
|
me.baseGui.Close()
|
||||||
|
exit("forced exit() from within gocui")
|
||||||
|
return nil
|
||||||
|
})
|
||||||
|
g.SetKeybinding("", gocui.KeyCtrlC, gocui.ModNone,
|
||||||
|
func(g *gocui.Gui, v *gocui.View) error {
|
||||||
|
me.baseGui.Close()
|
||||||
|
exit("forced exit() from within gocui")
|
||||||
|
return nil
|
||||||
|
})
|
||||||
|
|
||||||
// panic
|
// panic
|
||||||
g.SetKeybinding("", 'p', gocui.ModNone,
|
g.SetKeybinding("", 'p', gocui.ModNone,
|
||||||
func(g *gocui.Gui, v *gocui.View) error {
|
func(g *gocui.Gui, v *gocui.View) error {
|
||||||
|
me.baseGui.Close()
|
||||||
panic("forced panic in gocui")
|
panic("forced panic in gocui")
|
||||||
return nil
|
return nil
|
||||||
})
|
})
|
||||||
|
|
|
@ -34,7 +34,7 @@ func Callback(guiCallback chan toolkit.Action) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func Exit() {
|
func Exit() {
|
||||||
// TODO: exit correctly
|
// TODO: send exit to the plugin
|
||||||
me.baseGui.Close()
|
me.baseGui.Close()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -51,4 +51,5 @@ func Main(f func()) {
|
||||||
log("This is a test log entry")
|
log("This is a test log entry")
|
||||||
|
|
||||||
MouseMain()
|
MouseMain()
|
||||||
|
me.baseGui.Close()
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,8 +15,15 @@ func Action(a *toolkit.Action) {
|
||||||
w := findWidget(a.WidgetId, me.rootNode)
|
w := findWidget(a.WidgetId, me.rootNode)
|
||||||
switch a.ActionType {
|
switch a.ActionType {
|
||||||
case toolkit.Add:
|
case toolkit.Add:
|
||||||
w = makeWidget(a)
|
if (w == nil) {
|
||||||
w.addWidget()
|
w = makeWidget(a)
|
||||||
|
w.addWidget()
|
||||||
|
} else {
|
||||||
|
// this is done to protect the plugin being 'refreshed' with the
|
||||||
|
// widget binary tree. TODO: find a way to keep them in sync
|
||||||
|
log(logError, "Action() Add ignored for already defined widget",
|
||||||
|
a.WidgetId, a.ActionType, a.WidgetType, a.Name)
|
||||||
|
}
|
||||||
case toolkit.Show:
|
case toolkit.Show:
|
||||||
if (a.B) {
|
if (a.B) {
|
||||||
w.drawView()
|
w.drawView()
|
||||||
|
|
|
@ -15,7 +15,14 @@ var watchtime time.Duration = 100 // in tenths of seconds
|
||||||
func Watchdog() {
|
func Watchdog() {
|
||||||
var i = 1
|
var i = 1
|
||||||
for {
|
for {
|
||||||
log(logInfo, "watchdog timer is alive. give me something to do.", i)
|
log(logNow, "watchdog timer is alive. give me something to do.", i)
|
||||||
|
if (Config.rootNode == nil) {
|
||||||
|
log(logInfo, "Config.rootNode == nil", i)
|
||||||
|
} else {
|
||||||
|
if (logVerbose) {
|
||||||
|
Config.rootNode.ListChildren(true)
|
||||||
|
}
|
||||||
|
}
|
||||||
i += 1
|
i += 1
|
||||||
time.Sleep(watchtime * time.Second / 10)
|
time.Sleep(watchtime * time.Second / 10)
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue