commit
3ea3dd10db
|
@ -0,0 +1,4 @@
|
|||
redomod:
|
||||
rm -f go.*
|
||||
GO111MODULE= go mod init
|
||||
GO111MODULE= go mod tidy
|
|
@ -0,0 +1,47 @@
|
|||
package tree
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
||||
"go.wit.com/log"
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
// this is in common.go, do not move it
|
||||
func (me *TreeInfo) AddNode(a *widget.Action) *Node {
|
||||
n := new(Node)
|
||||
n.WidgetType = a.WidgetType
|
||||
n.WidgetId = a.WidgetId
|
||||
n.ParentId = a.ParentId
|
||||
|
||||
n.State = a.State
|
||||
n.Strings = make(map[string]int)
|
||||
|
||||
if (a.WidgetType == widget.Root) {
|
||||
log.Info("AddNode() Root")
|
||||
n.Parent = n
|
||||
me.treeRoot = n
|
||||
return n
|
||||
}
|
||||
|
||||
if (me.treeRoot.FindWidgetId(a.WidgetId) != nil) {
|
||||
log.Warn("AddNode() WidgetId already exists", a.WidgetId)
|
||||
log.Warn("probably this is a Show() / Hide() issue")
|
||||
log.Warn("TODO: figure out what to do here")
|
||||
return me.treeRoot.FindWidgetId(a.WidgetId)
|
||||
}
|
||||
|
||||
// add this new widget on the binary tree
|
||||
p := me.treeRoot.FindWidgetId(a.ParentId)
|
||||
n.Parent = p
|
||||
if n.Parent == nil {
|
||||
log.Error(errors.New("tree.AddNode() ERROR n.Parent == nil"), a.WidgetId, a.ParentId, a.ActionType)
|
||||
log.Warn("AddNode() ERROR n.Parent == nil", a.WidgetId, a.ParentId, a.ActionType)
|
||||
log.Warn("AddNode() ERROR n.Parent == nil", a.WidgetId, a.ParentId, a.WidgetType)
|
||||
return n
|
||||
}
|
||||
log.Warn("AddNode() Adding to parent =", p.ParentId, p.WidgetType, p.GetProgName())
|
||||
log.Warn("AddNode() Adding child =", n.ParentId, n.WidgetType, n.GetProgName())
|
||||
p.children = append(p.children, n)
|
||||
return n
|
||||
}
|
|
@ -0,0 +1,35 @@
|
|||
package tree
|
||||
|
||||
import (
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
func (n *Node) GetProgName() string {
|
||||
return n.State.ProgName
|
||||
}
|
||||
|
||||
func (n *Node) GetValue() any {
|
||||
return n.State.Value
|
||||
}
|
||||
|
||||
func (n *Node) Bool() bool {
|
||||
return widget.GetBool(n.State.Value)
|
||||
}
|
||||
|
||||
func (n *Node) String() string {
|
||||
return widget.GetString(n.State.Value)
|
||||
}
|
||||
|
||||
/* avoid this function name as confusing
|
||||
func (n *Node) GetText() string {
|
||||
return widget.GetString(n.State.Value)
|
||||
}
|
||||
*/
|
||||
|
||||
func (n *Node) SetValue(a any) {
|
||||
n.State.Value = a
|
||||
}
|
||||
|
||||
func (n *Node) GetLabel() string {
|
||||
return n.State.Label
|
||||
}
|
|
@ -0,0 +1,44 @@
|
|||
package tree
|
||||
|
||||
import (
|
||||
"go.wit.com/log"
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
func (n *Node) ShowButtons() {
|
||||
if n.WidgetType == widget.Button {
|
||||
n.DumpWidget("Button:")
|
||||
}
|
||||
|
||||
for _, child := range n.children {
|
||||
child.ShowButtons()
|
||||
}
|
||||
}
|
||||
|
||||
func (n *Node) DumpWidget(pad string) {
|
||||
log.Warn("node:", pad, n.WidgetId, ",", n.WidgetType, ",", n.GetProgName())
|
||||
}
|
||||
|
||||
var depth int = 0
|
||||
|
||||
func (n *Node) ListWidgets() {
|
||||
if (n == nil) {
|
||||
log.Warn("ERRRORRRR: n == nil in ListWidgets()")
|
||||
log.Warn("ERRRORRRR: n == nil in ListWidgets()")
|
||||
log.Warn("ERRRORRRR: n == nil in ListWidgets()")
|
||||
return
|
||||
}
|
||||
|
||||
var pad string
|
||||
for i := 0; i < depth; i++ {
|
||||
pad = pad + " "
|
||||
}
|
||||
n.DumpWidget(pad)
|
||||
|
||||
for _, child := range n.children {
|
||||
depth += 1
|
||||
child.ListWidgets()
|
||||
depth -= 1
|
||||
}
|
||||
return
|
||||
}
|
|
@ -0,0 +1,88 @@
|
|||
package tree
|
||||
|
||||
/*
|
||||
These code should be common to all gui plugins
|
||||
|
||||
There are some helper functions that are probably going to be
|
||||
the same everywhere. Mostly due to handling the binary tree structure
|
||||
and the channel communication
|
||||
|
||||
For now, it's just a symlink to the 'master' version in
|
||||
./toolkit/nocui/common.go
|
||||
*/
|
||||
|
||||
import (
|
||||
"go.wit.com/log"
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
func (me *TreeInfo) DoEnableDebugger() {
|
||||
if (me.callback == nil) {
|
||||
log.Warn("DoUserEvent() toolkit panic() callback == nil")
|
||||
return
|
||||
}
|
||||
var a widget.Action
|
||||
a.ActionType = widget.EnableDebug
|
||||
a.ProgName = me.PluginName
|
||||
me.callback <- a
|
||||
return
|
||||
}
|
||||
|
||||
func (me *TreeInfo) DoToolkitLoad(s string) {
|
||||
if (me.callback == nil) {
|
||||
log.Warn("DoUserEvent() toolkit load callback == nil")
|
||||
return
|
||||
}
|
||||
var a widget.Action
|
||||
a.ActionType = widget.ToolkitLoad
|
||||
a.ProgName = me.PluginName
|
||||
a.Value = s
|
||||
log.Warn("DoUserEvent() START: toolkit load", s)
|
||||
me.callback <- a
|
||||
log.Warn("DoUserEvent() END: toolkit load", s)
|
||||
return
|
||||
}
|
||||
|
||||
func (me *TreeInfo) DoToolkitPanic() {
|
||||
if (me.callback == nil) {
|
||||
log.Warn("DoUserEvent() toolkit panic() callback == nil")
|
||||
return
|
||||
}
|
||||
var a widget.Action
|
||||
a.ActionType = widget.ToolkitPanic
|
||||
a.ProgName = me.PluginName
|
||||
log.Info("DoUserEvent() START: toolkit panic()")
|
||||
me.callback <- a
|
||||
log.Info("DoUserEvent() END: toolkit panic()")
|
||||
return
|
||||
}
|
||||
|
||||
func (me *TreeInfo) DoWindowCloseEvent(n *Node) {
|
||||
if (me.callback == nil) {
|
||||
log.Warn("DoUserEvent() callback == nil", n.WidgetId)
|
||||
return
|
||||
}
|
||||
var a widget.Action
|
||||
a.WidgetId = n.WidgetId
|
||||
a.ActionType = widget.CloseWindow
|
||||
log.Info("DoUserEvent() START: user closed the window", n.GetProgName())
|
||||
me.callback <- a
|
||||
log.Info("DoUserEvent() END: user closed the window", n.GetProgName())
|
||||
return
|
||||
}
|
||||
|
||||
// Other goroutines must use this to access the GUI
|
||||
func (me *TreeInfo) DoUserEvent(n *Node) {
|
||||
if (me.callback == nil) {
|
||||
log.Warn("DoUserEvent() callback == nil", n.WidgetId)
|
||||
return
|
||||
}
|
||||
var a widget.Action
|
||||
a.WidgetId = n.WidgetId
|
||||
a.Value = n.State.Value
|
||||
a.ActionType = widget.User
|
||||
log.Info("DoUserEvent() START: send a user event to the callback channel")
|
||||
me.callback <- a
|
||||
log.Info("DoUserEvent() END: sent a user event to the callback channel")
|
||||
return
|
||||
}
|
|
@ -0,0 +1,10 @@
|
|||
module go.wit.com/toolkits/tree
|
||||
|
||||
go 1.21.4
|
||||
|
||||
require (
|
||||
go.wit.com/gui/widget v1.1.4
|
||||
go.wit.com/log v0.5.5
|
||||
)
|
||||
|
||||
require go.wit.com/dev/davecgh/spew v1.1.4 // indirect
|
|
@ -0,0 +1,6 @@
|
|||
go.wit.com/dev/davecgh/spew v1.1.4 h1:C9hj/rjlUpdK+E6aroyLjCbS5MFcyNUOuP1ICLWdNek=
|
||||
go.wit.com/dev/davecgh/spew v1.1.4/go.mod h1:sihvWmnQ/09FWplnEmozt90CCVqBtGuPXM811tgfhFA=
|
||||
go.wit.com/gui/widget v1.1.4 h1:dCztWNSuTSSP+/M8h8F3cT7vWtoKdCL3DUQql0qLKdk=
|
||||
go.wit.com/gui/widget v1.1.4/go.mod h1:A6/FaiFQtAHTjgo7c4FrokXe6bXX1Cowo35b2Lgi31E=
|
||||
go.wit.com/log v0.5.5 h1:bK3b94uVKgev4jB5wg06FnvCFBEapQICTSH2YW+CWr4=
|
||||
go.wit.com/log v0.5.5/go.mod h1:BaJBfHFqcJSJLXGQ9RHi3XVhPgsStxSMZRlaRxW4kAo=
|
|
@ -0,0 +1,58 @@
|
|||
package tree
|
||||
|
||||
import (
|
||||
"sync"
|
||||
"errors"
|
||||
|
||||
"go.wit.com/log"
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
var muAction sync.Mutex
|
||||
|
||||
func (me *TreeInfo) toolkit(a widget.Action) {
|
||||
if me.ActionFromChannel == nil {
|
||||
log.Error(errors.New("toolkit ActionFromChannel == nil"), a.WidgetId, a.ActionType, a.WidgetType)
|
||||
return
|
||||
}
|
||||
me.ActionFromChannel(a)
|
||||
}
|
||||
|
||||
func (me *TreeInfo) catchActionChannel() {
|
||||
defer func() {
|
||||
if r := recover(); r != nil {
|
||||
log.Warn("nocui YAHOOOO Recovered in simpleStdin()", r)
|
||||
me.DoToolkitPanic()
|
||||
panic(-1)
|
||||
}
|
||||
}()
|
||||
log.Info("catchActionChannel() START")
|
||||
for {
|
||||
log.Info("catchActionChannel() for loop")
|
||||
select {
|
||||
case a := <-me.pluginChan:
|
||||
log.Info("catchActionChannel() SELECT widget id =", a.WidgetId, a.ProgName)
|
||||
log.Warn("catchActionChannel() STUFF", a.WidgetId, a.ActionType, a.WidgetType)
|
||||
if a.WidgetType == widget.Dropdown {
|
||||
log.Warn("Found dropdown", a.WidgetId, a.ActionType, a.WidgetType)
|
||||
for i, s := range a.State.Strings {
|
||||
log.Warn("a.State.Strings =", i, s)
|
||||
}
|
||||
}
|
||||
muAction.Lock()
|
||||
me.toolkit(a)
|
||||
muAction.Unlock()
|
||||
log.Info("catchActionChannel() STUFF END", a.WidgetId, a.ActionType, a.WidgetType)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func New() *TreeInfo {
|
||||
me := new(TreeInfo)
|
||||
me.pluginChan = make(chan widget.Action, 1)
|
||||
|
||||
log.Info("Init() start channel reciever")
|
||||
go me.catchActionChannel()
|
||||
log.Info("Init() END")
|
||||
return me
|
||||
}
|
|
@ -0,0 +1,60 @@
|
|||
package tree
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"go.wit.com/log"
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
// makes a JSON version to pass to the toolkits ?
|
||||
// probably this should be in gui/toolkits/tree
|
||||
/*
|
||||
{"widget": {
|
||||
"debug": "on",
|
||||
"window": {
|
||||
"title": "Sample Konfabulator Widget",
|
||||
"name": "main_window",
|
||||
"width": 500,
|
||||
"height": 500
|
||||
},
|
||||
"image": {
|
||||
"src": "Images/Sun.png",
|
||||
"name": "sun1",
|
||||
"hOffset": 250,
|
||||
"vOffset": 250,
|
||||
"alignment": "center"
|
||||
},
|
||||
"text": {
|
||||
"data": "Click Here",
|
||||
"size": 36,
|
||||
"style": "bold",
|
||||
"name": "text1",
|
||||
"hOffset": 250,
|
||||
"vOffset": 100,
|
||||
"alignment": "center",
|
||||
"onMouseUp": "sun1.opacity = (sun1.opacity / 100) * 90;"
|
||||
}
|
||||
}}
|
||||
*/
|
||||
|
||||
func (n *Node) Json() []string {
|
||||
var all []string
|
||||
switch n.WidgetType {
|
||||
case widget.Checkbox:
|
||||
case widget.Button:
|
||||
case widget.Combobox:
|
||||
case widget.Dropdown:
|
||||
case widget.Textbox:
|
||||
case widget.Spinner:
|
||||
case widget.Slider:
|
||||
case widget.Window:
|
||||
tmp := fmt.Sprint("{ WidgetType :", n.WidgetType, "}")
|
||||
all = append(all, tmp)
|
||||
log.Warn(tmp)
|
||||
return all
|
||||
default:
|
||||
log.Info("doUserEvent() type =", n.WidgetType)
|
||||
}
|
||||
return all
|
||||
}
|
|
@ -0,0 +1,50 @@
|
|||
package tree
|
||||
|
||||
/*
|
||||
These code should be common to all gui plugins
|
||||
|
||||
There are some helper functions that are probably going to be
|
||||
the same everywhere. Mostly due to handling the binary tree structure
|
||||
and the channel communication
|
||||
|
||||
For now, it's just a symlink to the 'master' version in
|
||||
./toolkit/nocui/common.go
|
||||
*/
|
||||
|
||||
import (
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
// searches the binary tree for a WidgetId
|
||||
func (n *Node) FindWidgetId(id int) *Node {
|
||||
if (n == nil) {
|
||||
return nil
|
||||
}
|
||||
|
||||
if n.WidgetId == id {
|
||||
return n
|
||||
}
|
||||
|
||||
for _, child := range n.children {
|
||||
newN := child.FindWidgetId(id)
|
||||
if (newN != nil) {
|
||||
return newN
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// Other goroutines must use this to access the GUI
|
||||
//
|
||||
// You can not acess / process the GUI thread directly from
|
||||
// other goroutines. This is due to the nature of how
|
||||
// Linux, MacOS and Windows work (they all work differently. suprise. surprise.)
|
||||
//
|
||||
// this sets the channel to send user events back from the plugin
|
||||
func (me *TreeInfo) Callback(guiCallback chan widget.Action) {
|
||||
me.callback = guiCallback
|
||||
}
|
||||
|
||||
func (me *TreeInfo) PluginChannel() chan widget.Action {
|
||||
return me.pluginChan
|
||||
}
|
|
@ -0,0 +1,51 @@
|
|||
package tree
|
||||
|
||||
/*
|
||||
These code should be common to all gui plugins
|
||||
|
||||
There are some helper functions that are probably going to be
|
||||
the same everywhere. Mostly due to handling the binary tree structure
|
||||
and the channel communication
|
||||
|
||||
For now, it's just a symlink to the 'master' version in
|
||||
./toolkit/nocui/common.go
|
||||
*/
|
||||
|
||||
import (
|
||||
// "go.wit.com/log"
|
||||
"go.wit.com/lib/widget"
|
||||
)
|
||||
|
||||
// var me *TreeInfo
|
||||
|
||||
type TreeInfo struct {
|
||||
// this is the channel we send user events like
|
||||
// mouse clicks or keyboard events back to the program
|
||||
callback chan widget.Action
|
||||
|
||||
// this is the channel we get requests to make widgets
|
||||
pluginChan chan widget.Action
|
||||
|
||||
treeRoot *Node
|
||||
NodeI interface {}
|
||||
ActionFromChannel func (widget.Action) ()
|
||||
PluginName string
|
||||
}
|
||||
|
||||
type Node struct {
|
||||
Parent *Node
|
||||
children []*Node
|
||||
|
||||
WidgetId int // widget ID
|
||||
WidgetType widget.WidgetType
|
||||
ParentId int // parent ID
|
||||
|
||||
State widget.State
|
||||
|
||||
Strings map[string]int
|
||||
|
||||
// the internal plugin toolkit structure
|
||||
// in the gtk plugin, it has gtk things like margin & border settings
|
||||
// in the text console one, it has text console things like colors for menus & buttons
|
||||
TK any
|
||||
}
|
Loading…
Reference in New Issue