andlabs: ran without crashing
Signed-off-by: Jeff Carr <jcarr@wit.com>
This commit is contained in:
parent
1986bd286d
commit
28280403bf
|
@ -123,14 +123,7 @@ Creates a window helpful for debugging this package
|
||||||
|
|
||||||
`func ExampleCatcher(f func())`
|
`func ExampleCatcher(f func())`
|
||||||
|
|
||||||
### func [FindPlugin](/plugin.go#L64)
|
### func [Indent](/debug.go#L126)
|
||||||
|
|
||||||
`func FindPlugin(name string) *aplug`
|
|
||||||
|
|
||||||
loads and initializes a toolkit (andlabs/ui, gocui, etc)
|
|
||||||
attempts to locate the .so file
|
|
||||||
|
|
||||||
### func [Indent](/debug.go#L120)
|
|
||||||
|
|
||||||
`func Indent(b bool, a ...interface{})`
|
`func Indent(b bool, a ...interface{})`
|
||||||
|
|
||||||
|
@ -138,15 +131,15 @@ attempts to locate the .so file
|
||||||
|
|
||||||
`func SetDebug(s bool)`
|
`func SetDebug(s bool)`
|
||||||
|
|
||||||
### func [SetFlag](/debug.go#L44)
|
### func [SetFlag](/debug.go#L50)
|
||||||
|
|
||||||
`func SetFlag(s string, b bool)`
|
`func SetFlag(s string, b bool)`
|
||||||
|
|
||||||
### func [ShowDebugValues](/debug.go#L79)
|
### func [ShowDebugValues](/debug.go#L85)
|
||||||
|
|
||||||
`func ShowDebugValues()`
|
`func ShowDebugValues()`
|
||||||
|
|
||||||
### func [StandardExit](/main.go#L169)
|
### func [StandardExit](/main.go#L180)
|
||||||
|
|
||||||
`func StandardExit()`
|
`func StandardExit()`
|
||||||
|
|
||||||
|
@ -187,7 +180,7 @@ var Config GuiConfig
|
||||||
The Node is a binary tree. This is how all GUI elements are stored
|
The Node is a binary tree. This is how all GUI elements are stored
|
||||||
simply the name and the size of whatever GUI element exists
|
simply the name and the size of whatever GUI element exists
|
||||||
|
|
||||||
#### func [New](/main.go#L142)
|
#### func [New](/main.go#L153)
|
||||||
|
|
||||||
`func New() *Node`
|
`func New() *Node`
|
||||||
|
|
||||||
|
|
|
@ -16,7 +16,7 @@ var buttonCounter int = 5
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
// This will turn on all debugging
|
// This will turn on all debugging
|
||||||
// gui.SetDebug(true)
|
gui.SetDebug(true)
|
||||||
|
|
||||||
// myGui = gui.New().LoadToolkit("gocui")
|
// myGui = gui.New().LoadToolkit("gocui")
|
||||||
myGui = gui.New().LoadToolkit("andlabs")
|
myGui = gui.New().LoadToolkit("andlabs")
|
||||||
|
|
6
debug.go
6
debug.go
|
@ -29,6 +29,12 @@ func SetDebug (s bool) {
|
||||||
debugGui = s
|
debugGui = s
|
||||||
debugTabs = s
|
debugTabs = s
|
||||||
|
|
||||||
|
logNow = s
|
||||||
|
logInfo = s
|
||||||
|
logWarn = s
|
||||||
|
logError = s
|
||||||
|
logVerbose = s
|
||||||
|
|
||||||
SetFlag("Node", s)
|
SetFlag("Node", s)
|
||||||
SetFlag("Tabs", s)
|
SetFlag("Tabs", s)
|
||||||
SetFlag("Dump", s)
|
SetFlag("Dump", s)
|
||||||
|
|
31
main.go
31
main.go
|
@ -112,22 +112,33 @@ func (n *Node) doUserEvent(a toolkit.Action) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *Node) LoadToolkit(name string) *Node {
|
func (n *Node) LoadToolkit(name string) *Node {
|
||||||
log(logInfo, "LoadToolkit() for name =", name)
|
log(logInfo, "LoadToolkit() START for name =", name)
|
||||||
if (FindPlugin(name) == nil) {
|
plug := initPlugin(name)
|
||||||
|
if (plug == nil) {
|
||||||
return n
|
return n
|
||||||
}
|
}
|
||||||
|
|
||||||
|
log(logInfo, "LoadToolkit() sending InitToolkit action to the plugin channel")
|
||||||
|
var a toolkit.Action
|
||||||
|
a.ActionType = toolkit.InitToolkit
|
||||||
|
plug.pluginChan <- a
|
||||||
|
sleep(.5) // temp hack until chan communication is setup
|
||||||
|
|
||||||
|
// TODO: find a new way to do this that is locking, safe and accurate
|
||||||
|
Config.rootNode.redraw(plug)
|
||||||
|
log(logInfo, "LoadToolkit() END for name =", name)
|
||||||
return n
|
return n
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *Node) CloseToolkit(name string) bool {
|
func (n *Node) CloseToolkit(name string) bool {
|
||||||
log(logInfo, "CloseToolkit() for name =", name)
|
log(logInfo, "CloseToolkit() for name =", name)
|
||||||
for _, aplug := range allPlugins {
|
for _, plug := range allPlugins {
|
||||||
log(debugGui, "CloseToolkit() found", aplug.name)
|
log(debugGui, "CloseToolkit() found", plug.name)
|
||||||
if (aplug.name == name) {
|
if (plug.name == name) {
|
||||||
log(debugNow, "CloseToolkit() sending close", name)
|
log(debugNow, "CloseToolkit() sending close", name)
|
||||||
var a toolkit.Action
|
var a toolkit.Action
|
||||||
a.ActionType = toolkit.CloseToolkit
|
a.ActionType = toolkit.CloseToolkit
|
||||||
aplug.pluginChan <- a
|
plug.pluginChan <- a
|
||||||
sleep(.5)
|
sleep(.5)
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
@ -144,7 +155,7 @@ func New() *Node {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *Node) Default() *Node {
|
func (n *Node) Default() *Node {
|
||||||
if (FindPlugin("gocui") == nil) {
|
if (n.LoadToolkit("gocui") == nil) {
|
||||||
log(logError, "New() failed to load gocui")
|
log(logError, "New() failed to load gocui")
|
||||||
}
|
}
|
||||||
// if DISPLAY isn't set, return since gtk can't load
|
// if DISPLAY isn't set, return since gtk can't load
|
||||||
|
@ -152,7 +163,7 @@ func (n *Node) Default() *Node {
|
||||||
if (os.Getenv("DISPLAY") == "") {
|
if (os.Getenv("DISPLAY") == "") {
|
||||||
return n
|
return n
|
||||||
}
|
}
|
||||||
if (FindPlugin("andlabs") == nil) {
|
if (n.LoadToolkit("andlabs") == nil) {
|
||||||
log(logError, "New() failed to load andlabs")
|
log(logError, "New() failed to load andlabs")
|
||||||
}
|
}
|
||||||
return n
|
return n
|
||||||
|
@ -169,8 +180,8 @@ func (n *Node) StandardClose() {
|
||||||
func StandardExit() {
|
func StandardExit() {
|
||||||
log("wit/gui Standard Window Exit. running os.Exit()")
|
log("wit/gui Standard Window Exit. running os.Exit()")
|
||||||
log("StandardExit() attempt to exit each toolkit plugin")
|
log("StandardExit() attempt to exit each toolkit plugin")
|
||||||
for i, aplug := range allPlugins {
|
for i, plug := range allPlugins {
|
||||||
log("NewButton()", i, aplug)
|
log("NewButton()", i, plug)
|
||||||
}
|
}
|
||||||
exit(0)
|
exit(0)
|
||||||
}
|
}
|
||||||
|
|
141
plugin.go
141
plugin.go
|
@ -16,17 +16,14 @@ var err error
|
||||||
type Symbol any
|
type Symbol any
|
||||||
|
|
||||||
type aplug struct {
|
type aplug struct {
|
||||||
// Ok bool
|
|
||||||
name string
|
name string
|
||||||
filename string
|
filename string
|
||||||
plug *plugin.Plugin
|
plug *plugin.Plugin
|
||||||
sym *plugin.Symbol
|
// sym *plugin.Symbol
|
||||||
// LoadOk bool
|
|
||||||
InitOk bool
|
InitOk bool
|
||||||
// MainOk bool
|
|
||||||
|
|
||||||
// startup whatever might need to be setup in the plugin
|
// startup whatever might need to be setup in the plugin
|
||||||
Init func()
|
// Init func()
|
||||||
|
|
||||||
// This passes the go channel to the plugin
|
// This passes the go channel to the plugin
|
||||||
// the plugin then passes actions back to
|
// the plugin then passes actions back to
|
||||||
|
@ -49,33 +46,27 @@ type aplug struct {
|
||||||
// add button request
|
// add button request
|
||||||
pluginChan chan toolkit.Action
|
pluginChan chan toolkit.Action
|
||||||
PluginChannel func() chan toolkit.Action
|
PluginChannel func() chan toolkit.Action
|
||||||
|
|
||||||
// deprecate all this
|
|
||||||
// TODO: make Main() main() and never allow the user to call it
|
|
||||||
// run plugin.Main() when the plugin is loaded
|
|
||||||
// Main func(func ()) // this never returns. Each plugin must have it's own goroutine
|
|
||||||
// Quit func()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
var allPlugins []*aplug
|
var allPlugins []*aplug
|
||||||
|
|
||||||
// loads and initializes a toolkit (andlabs/ui, gocui, etc)
|
// loads and initializes a toolkit (andlabs/ui, gocui, etc)
|
||||||
// attempts to locate the .so file
|
// attempts to locate the .so file
|
||||||
func FindPlugin(name string) *aplug {
|
func initPlugin(name string) *aplug {
|
||||||
var newPlug *aplug
|
log(logInfo, "initPlugin() START")
|
||||||
newPlug = new(aplug)
|
|
||||||
|
|
||||||
log(logInfo, "FindPlugin() START")
|
|
||||||
newPlug.InitOk = false
|
|
||||||
|
|
||||||
for _, aplug := range allPlugins {
|
for _, aplug := range allPlugins {
|
||||||
log(debugGui, "FindPlugin() already loaded toolkit plugin =", aplug.name)
|
log(debugGui, "initPlugin() already loaded toolkit plugin =", aplug.name)
|
||||||
if (aplug.name == name) {
|
if (aplug.name == name) {
|
||||||
log(debugError, "FindPlugin() SKIPPING", name, "as you can't load it twice")
|
log(debugError, "initPlugin() SKIPPING", name, "as you can't load it twice")
|
||||||
return aplug
|
return nil
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var newPlug *aplug
|
||||||
|
newPlug = new(aplug)
|
||||||
|
newPlug.InitOk = false
|
||||||
|
|
||||||
// locate the shared library file
|
// locate the shared library file
|
||||||
filename := name + ".so"
|
filename := name + ".so"
|
||||||
loadPlugin(newPlug, filename)
|
loadPlugin(newPlug, filename)
|
||||||
|
@ -86,22 +77,6 @@ func FindPlugin(name string) *aplug {
|
||||||
// newPlug.Ok = true
|
// newPlug.Ok = true
|
||||||
newPlug.name = name
|
newPlug.name = name
|
||||||
|
|
||||||
// deprecate Init(?)
|
|
||||||
newPlug.Init = loadFuncE(newPlug, "Init")
|
|
||||||
|
|
||||||
// should make a goroutine that never exits
|
|
||||||
// newPlug.Main = loadFuncF(newPlug, "Main")
|
|
||||||
|
|
||||||
// should send things to the goroutine above
|
|
||||||
// newPlug.Queue = loadFuncF(&newPlug, "Queue")
|
|
||||||
|
|
||||||
// unload the plugin and restore state
|
|
||||||
// newPlug.Quit = loadFuncE(newPlug, "Quit")
|
|
||||||
|
|
||||||
// Sends instructions like "Add", "Delete", "Disable", etc
|
|
||||||
// Sends a widget (button, checkbox, etc) and it's parent widget
|
|
||||||
// newPlug.Action = loadFuncA(newPlug, "Action")
|
|
||||||
|
|
||||||
// this tells the toolkit plugin how to send user events back to us
|
// this tells the toolkit plugin how to send user events back to us
|
||||||
// for things like: the user clicked on the 'Check IPv6'
|
// for things like: the user clicked on the 'Check IPv6'
|
||||||
newPlug.Callback = sendCallback(newPlug, "Callback")
|
newPlug.Callback = sendCallback(newPlug, "Callback")
|
||||||
|
@ -112,8 +87,8 @@ func FindPlugin(name string) *aplug {
|
||||||
|
|
||||||
allPlugins = append(allPlugins, newPlug)
|
allPlugins = append(allPlugins, newPlug)
|
||||||
|
|
||||||
log(debugPlugin, "FindPlugin() END", newPlug.name, filename)
|
log(debugPlugin, "initPlugin() END", newPlug.name, filename)
|
||||||
newPlug.Init()
|
// newPlug.Init()
|
||||||
|
|
||||||
// set the communication to the plugins
|
// set the communication to the plugins
|
||||||
newPlug.pluginChan = newPlug.PluginChannel()
|
newPlug.pluginChan = newPlug.PluginChannel()
|
||||||
|
@ -121,35 +96,9 @@ func FindPlugin(name string) *aplug {
|
||||||
|
|
||||||
newPlug.InitOk = true
|
newPlug.InitOk = true
|
||||||
|
|
||||||
sleep(1) // temp hack until chan communication is setup
|
|
||||||
|
|
||||||
// TODO: find a new way to do this that is locking, safe and accurate
|
|
||||||
Config.rootNode.redraw(newPlug)
|
|
||||||
|
|
||||||
return newPlug
|
return newPlug
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: All these functions need to be done a smarter way
|
|
||||||
// but I haven't worked out the golang syntax to make it smarter
|
|
||||||
func loadFuncE(p *aplug, funcName string) func() {
|
|
||||||
var newfunc func()
|
|
||||||
var ok bool
|
|
||||||
var test plugin.Symbol
|
|
||||||
|
|
||||||
test, err = p.plug.Lookup(funcName)
|
|
||||||
if err != nil {
|
|
||||||
log(debugGui, "DID NOT FIND: name =", test, "err =", err)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
newfunc, ok = test.(func())
|
|
||||||
if !ok {
|
|
||||||
log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
return newfunc
|
|
||||||
}
|
|
||||||
|
|
||||||
// newPlug.PluginChannel = getPluginChannel(newPlug, "PluginChannel")
|
// newPlug.PluginChannel = getPluginChannel(newPlug, "PluginChannel")
|
||||||
func getPluginChannel(p *aplug, funcName string) func() chan toolkit.Action {
|
func getPluginChannel(p *aplug, funcName string) func() chan toolkit.Action {
|
||||||
var newfunc func() chan toolkit.Action
|
var newfunc func() chan toolkit.Action
|
||||||
|
@ -189,70 +138,6 @@ func sendCallback(p *aplug, funcName string) func(chan toolkit.Action) {
|
||||||
return newfunc
|
return newfunc
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
func loadFunc2(p *aplug, funcName string) func(*toolkit.Widget, *toolkit.Widget) {
|
|
||||||
var newfunc func(*toolkit.Widget, *toolkit.Widget)
|
|
||||||
var ok bool
|
|
||||||
var test plugin.Symbol
|
|
||||||
|
|
||||||
test, err = p.plug.Lookup(funcName)
|
|
||||||
if err != nil {
|
|
||||||
log(debugGui, "DID NOT FIND: name =", test, "err =", err)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
newfunc, ok = test.(func(*toolkit.Widget, *toolkit.Widget))
|
|
||||||
if !ok {
|
|
||||||
log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
return newfunc
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
// does this fix loadFuncE problems?
|
|
||||||
// TODO: still need to move to channels here
|
|
||||||
func loadFuncA(p *aplug, funcName string) func(*toolkit.Action) {
|
|
||||||
var newfunc func(*toolkit.Action)
|
|
||||||
var ok bool
|
|
||||||
var test plugin.Symbol
|
|
||||||
|
|
||||||
test, err = p.plug.Lookup(funcName)
|
|
||||||
if err != nil {
|
|
||||||
log(debugGui, "DID NOT FIND: name =", test, "err =", err)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
newfunc, ok = test.(func(*toolkit.Action))
|
|
||||||
if !ok {
|
|
||||||
log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
return newfunc
|
|
||||||
}
|
|
||||||
|
|
||||||
// This is probably dangerous and should never be done
|
|
||||||
// executing arbitrary functions will cause them to run inside the goroutine that
|
|
||||||
// the GUI toolkit itself is running in. TODO: move to channels here
|
|
||||||
func loadFuncF(p *aplug, funcName string) func(func ()) {
|
|
||||||
var newfunc func(func ())
|
|
||||||
var ok bool
|
|
||||||
var test plugin.Symbol
|
|
||||||
|
|
||||||
test, err = p.plug.Lookup(funcName)
|
|
||||||
if err != nil {
|
|
||||||
log(debugGui, "DID NOT FIND: name =", test, "err =", err)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
newfunc, ok = test.(func(func ()))
|
|
||||||
if !ok {
|
|
||||||
log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
return newfunc
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
This searches in the following order for the plugin .so files:
|
This searches in the following order for the plugin .so files:
|
||||||
./toolkit/
|
./toolkit/
|
||||||
|
|
|
@ -24,9 +24,6 @@ func catchActionChannel() {
|
||||||
log(logNow, "catchActionChannel() START")
|
log(logNow, "catchActionChannel() START")
|
||||||
for {
|
for {
|
||||||
log(logNow, "catchActionChannel() for loop")
|
log(logNow, "catchActionChannel() for loop")
|
||||||
uiMain.Do(func() {
|
|
||||||
go ui.Main(demoUI)
|
|
||||||
})
|
|
||||||
select {
|
select {
|
||||||
case a := <-pluginChan:
|
case a := <-pluginChan:
|
||||||
log(logNow, "catchActionChannel() SELECT widget id =", a.WidgetId, a.Name)
|
log(logNow, "catchActionChannel() SELECT widget id =", a.WidgetId, a.Name)
|
||||||
|
@ -95,7 +92,7 @@ func queue(f func()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// This is important. This sets the defaults for the gui. Without this, there isn't correct padding, etc
|
// This is important. This sets the defaults for the gui. Without this, there isn't correct padding, etc
|
||||||
func Init() {
|
func init() {
|
||||||
log(logNow, "Init() START")
|
log(logNow, "Init() START")
|
||||||
log(debugToolkit, "Init()")
|
log(debugToolkit, "Init()")
|
||||||
// Can you pass values to a plugin init() ? Otherwise, there is no way to safely print
|
// Can you pass values to a plugin init() ? Otherwise, there is no way to safely print
|
||||||
|
@ -106,7 +103,17 @@ func Init() {
|
||||||
pluginChan = make(chan toolkit.Action, 1)
|
pluginChan = make(chan toolkit.Action, 1)
|
||||||
|
|
||||||
log(logNow, "Init() start channel reciever")
|
log(logNow, "Init() start channel reciever")
|
||||||
|
go ui.Main(func() {
|
||||||
|
demoUI()
|
||||||
|
})
|
||||||
go catchActionChannel()
|
go catchActionChannel()
|
||||||
|
/*
|
||||||
|
// go catchActionChannel()
|
||||||
|
go uiMain.Do(func() {
|
||||||
|
ui.Main(demoUI)
|
||||||
|
// go catchActionChannel()
|
||||||
|
})
|
||||||
|
*/
|
||||||
log(logNow, "Init() END")
|
log(logNow, "Init() END")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -24,6 +24,7 @@ func Send(p *toolkit.Widget, c *toolkit.Widget) {
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
func oldAction2(a *toolkit.Action) {
|
func oldAction2(a *toolkit.Action) {
|
||||||
log(logNow, "Action() START")
|
log(logNow, "Action() START")
|
||||||
if (a == nil) {
|
if (a == nil) {
|
||||||
|
@ -31,22 +32,31 @@ func oldAction2(a *toolkit.Action) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
pluginChan <- *a
|
pluginChan <- *a
|
||||||
/*
|
|
||||||
f := func() {
|
f := func() {
|
||||||
rawAction(a)
|
rawAction(a)
|
||||||
}
|
}
|
||||||
|
|
||||||
// f()
|
// f()
|
||||||
Queue(f)
|
Queue(f)
|
||||||
*/
|
|
||||||
log(logNow, "Action() END")
|
log(logNow, "Action() END")
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
func rawAction(a toolkit.Action) {
|
func rawAction(a toolkit.Action) {
|
||||||
log(debugAction, "rawAction() START a.ActionType =", a.ActionType)
|
log(debugAction, "rawAction() START a.ActionType =", a.ActionType)
|
||||||
log(debugAction, "rawAction() START a.S =", a.S)
|
log(debugAction, "rawAction() START a.S =", a.S)
|
||||||
|
|
||||||
|
if (a.ActionType == toolkit.InitToolkit) {
|
||||||
|
// TODO: make sure to only do this once
|
||||||
|
// go uiMain.Do(func() {
|
||||||
|
// ui.Main(demoUI)
|
||||||
|
// go catchActionChannel()
|
||||||
|
// })
|
||||||
|
// try doing this on toolkit load in init()
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
log(logNow, "rawAction() START a.WidgetId =", a.WidgetId, "a.ParentId =", a.ParentId)
|
log(logNow, "rawAction() START a.WidgetId =", a.WidgetId, "a.ParentId =", a.ParentId)
|
||||||
switch a.WidgetType {
|
switch a.WidgetType {
|
||||||
case toolkit.Flag:
|
case toolkit.Flag:
|
||||||
|
|
|
@ -1,15 +1,7 @@
|
||||||
package toolkit
|
package toolkit
|
||||||
|
|
||||||
type WidgetType int
|
|
||||||
type ActionType int
|
|
||||||
|
|
||||||
// passes information between the toolkit library (plugin)
|
// passes information between the toolkit library (plugin)
|
||||||
//
|
//
|
||||||
// All Toolkit interactions should be done via a channel or Queue()
|
|
||||||
// TODO: FIGURE OUT HOW TO IMPLEMENT THIS
|
|
||||||
// https://ieftimov.com/post/golang-datastructures-trees/
|
|
||||||
// TODO: protobuf ?
|
|
||||||
//
|
|
||||||
// This is the only thing that is passed between the toolkit plugin
|
// This is the only thing that is passed between the toolkit plugin
|
||||||
//
|
//
|
||||||
// what names should be used? This is not part of [[Graphical Widget]]
|
// what names should be used? This is not part of [[Graphical Widget]]
|
||||||
|
@ -17,29 +9,12 @@ type ActionType int
|
||||||
// Event is used too much: web dev, cloud, etc
|
// Event is used too much: web dev, cloud, etc
|
||||||
// I'm using "Action". Maybe it should really be
|
// I'm using "Action". Maybe it should really be
|
||||||
// "Interaction" as per wikipedia [[User interface]]
|
// "Interaction" as per wikipedia [[User interface]]
|
||||||
// Could a protobuf be used here? (Can functions be passed?)
|
//
|
||||||
type Widget2 struct {
|
// TODO: convert this to a protobuf (?)
|
||||||
// Name string
|
//
|
||||||
Type WidgetType
|
|
||||||
|
|
||||||
// This function is how you interact with the toolkit
|
type WidgetType int // Button, Menu, Checkbox, etc.
|
||||||
// latest attempt. seems to work so far (2023/02/28)
|
type ActionType int // Add, SetText, Click, Hide, Append, Delete, etc
|
||||||
// Hopefully this will be the barrier between the goroutines
|
|
||||||
// TODO: move this interaction to channels
|
|
||||||
Custom func()
|
|
||||||
|
|
||||||
// re-adding an id to test channels
|
|
||||||
Id int
|
|
||||||
|
|
||||||
// This is how the values are passed back and forth
|
|
||||||
// values from things like checkboxes & dropdown's
|
|
||||||
// The string is also used to set the button name
|
|
||||||
B bool
|
|
||||||
I int
|
|
||||||
// maybe safe if there is correctly working Custom() between goroutines?
|
|
||||||
// (still probably not, almost certainly not. not possible. layer violation?)
|
|
||||||
S string // not safe to have 'S'
|
|
||||||
}
|
|
||||||
|
|
||||||
type Action struct {
|
type Action struct {
|
||||||
ActionType ActionType
|
ActionType ActionType
|
||||||
|
@ -51,20 +26,13 @@ type Action struct {
|
||||||
Text string // what is visable to the user
|
Text string // what is visable to the user
|
||||||
Name string // a name useful for programming
|
Name string // a name useful for programming
|
||||||
|
|
||||||
// this should be the widget
|
|
||||||
// if the action is New, Hide, Enable, etc
|
|
||||||
// Widget *Widget
|
|
||||||
|
|
||||||
// This is how the values are passed back and forth
|
// This is how the values are passed back and forth
|
||||||
// values from things like checkboxes & dropdown's
|
// values from things like checkboxes & dropdown's
|
||||||
// The string is also used to set the button name
|
|
||||||
B bool
|
B bool
|
||||||
I int
|
I int
|
||||||
// maybe safe if there is correctly working Custom() between goroutines?
|
S string
|
||||||
// (still probably not, almost certainly not. not possible. layer violation?)
|
|
||||||
S string // not safe to have 'S'
|
|
||||||
|
|
||||||
A any
|
A any // switch to this or deprecate this? pros/cons?
|
||||||
|
|
||||||
// This GUI is intended for simple things
|
// This GUI is intended for simple things
|
||||||
// We are not laying out PDF's here
|
// We are not laying out PDF's here
|
||||||
|
|
|
@ -23,12 +23,6 @@ func Watchdog() {
|
||||||
Config.rootNode.ListChildren(true)
|
Config.rootNode.ListChildren(true)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (i == 2) {
|
|
||||||
Config.rootNode.LoadToolkit("gocui")
|
|
||||||
}
|
|
||||||
// if (i == 3) {
|
|
||||||
// Config.rootNode.LoadToolkit("andlabs")
|
|
||||||
// }
|
|
||||||
i += 1
|
i += 1
|
||||||
time.Sleep(watchtime * time.Second / 10)
|
time.Sleep(watchtime * time.Second / 10)
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue