diff --git a/.gitignore b/.gitignore index 6bda501..84d756c 100644 --- a/.gitignore +++ b/.gitignore @@ -8,3 +8,7 @@ cmds/console-ui-helloworld/console-ui-helloworld cmds/debug/debug cmds/helloworld/helloworld cmds/textbox/textbox + +# temporary files when building debian packages +/*.deb +/files diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..6a66aea --- /dev/null +++ b/LICENSE @@ -0,0 +1,27 @@ +Copyright (c) 2009 The Go Authors. All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are +met: + + * Redistributions of source code must retain the above copyright +notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above +copyright notice, this list of conditions and the following disclaimer +in the documentation and/or other materials provided with the +distribution. + * Neither the name of Google Inc. nor the names of its +contributors may be used to endorse or promote products derived from +this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/Makefile b/Makefile index db08887..95b9d29 100644 --- a/Makefile +++ b/Makefile @@ -1,11 +1,12 @@ .PHONY: README.md all: README.md + reset @echo - @echo "make cmds # will run all the Example demos and commands" + @echo "make examples # will run all the Example demos and commands" @echo "make update # full git update of all the dependencies" @echo - #make -C cmds/helloworld + make clean make plugins # should update every go dependancy (?) @@ -13,7 +14,16 @@ update: git pull go get -v -t -u ./... -cmds: cmds-buttonplugin cmds-console-ui-helloworld cmds-debug cmds-helloworld cmds-textbox +deb: + cd debian && make + -wit mirrors + +examples: \ + cmds-buttonplugin \ + cmds-console-ui-helloworld \ + cmds-helloworld \ + cmds-debug \ + cmds-textbox cmds-buttonplugin: make -C cmds/buttonplugin @@ -51,6 +61,7 @@ README.md: doc.go clean: rm -f toolkit/*.so + cd debian && make clean plugins: plugins-gocui plugins-andlabs diff --git a/README-goreadme.md b/README-goreadme.md index 5125d3d..f21e4fe 100644 --- a/README-goreadme.md +++ b/README-goreadme.md @@ -93,74 +93,93 @@ hopefully also things like libSDL, faiface/pixel, slint ## References Useful links and other -external things -which might be useful +external things which might be useful [Wikipedia Graphical widget]: [https://en.wikipedia.org/wiki/Graphical_widget](https://en.wikipedia.org/wiki/Graphical_widget) [Github mirror]: [https://github.com/witorg/gui](https://github.com/witorg/gui) [Federated git pull]: [https://github.com/forgefed/forgefed](https://github.com/forgefed/forgefed) +[GO Style Guide]: [https://google.github.io/styleguide/go/index](https://google.github.io/styleguide/go/index) ```go * [Wikipedia Graphical widget] * [Github mirror] * [Federated git pull] +* [GO Style Guide] +``` + +version v1.3 + +I like things to be easy. + +this means all the log settings are in one place. it should allow +things to be over-ridden externally to the library +but still allow command line --args to pass debugging settings + +## I also have a generic sleep() and exit() in here because it's simple + +Usage: + +log("something", foo, bar) +var DEBUG bool = true +log(DEBUG, "something else", someOtherVariable) # if DEBUG == false, return doing nothing +log(SPEW, "something else", someOtherVariable) # this get's sent to spew.Dump(). Very useful for debugging! + +## Variables + +```golang +var INFO bool +``` + +```golang +var LOGOFF bool = false // turn this off, all logging stops + +``` + +```golang +var SPEW spewt +``` + +```golang +var WARN bool ``` ## Functions -### func [DebugTab](/example_window_debug.go#L26) - -`func DebugTab()` - -this function is used by the examples to add a tab -dynamically to the bugWin node -TODO: make this smarter once this uses toolkit/ - -### func [DebugWindow](/example_window_debug.go#L14) +### func [DebugWindow](/debug_window.go#L9) `func DebugWindow()` Creates a window helpful for debugging this package -### func [DemoWindow](/example_window_demo.go#L10) - -`func DemoWindow()` - -This creates a window that shows how this package works - -### func [GetDebug](/structs.go#L23) +### func [GetDebug](/debug.go#L20) `func GetDebug() bool` -### func [GetDebugToolkit](/structs.go#L34) - -`func GetDebugToolkit() bool` - -### func [GolangDebugWindow](/example_window_golang_debug.go#L12) +### func [GolangDebugWindow](/example_window_golang_debug.go#L10) `func GolangDebugWindow()` -### func [IndentPrintln](/structs.go#L159) +### func [Indent](/debug.go#L120) -`func IndentPrintln(a ...interface{})` +`func Indent(a ...interface{})` -### func [Init](/main.go#L41) +### func [InitPlugins](/main.go#L35) -`func Init()` +`func InitPlugins(names []string)` -### func [LoadToolkit](/plugin.go#L50) +### func [LoadToolkit](/plugin.go#L53) `func LoadToolkit(name string) bool` loads and initializes a toolkit (andlabs/ui, gocui, etc) -### func [Main](/main.go#L86) +### func [Main](/main.go#L76) `func Main(f func())` This should not pass a function -### func [Queue](/main.go#L115) +### func [Queue](/main.go#L106) `func Queue(f func())` @@ -171,31 +190,39 @@ other goroutines. This is due to the nature of how Linux, MacOS and Windows work (they all work differently. suprise. surprise.) For example: gui.Queue(NewWindow()) -### func [SetDebug](/structs.go#L27) +### func [SetDebug](/debug.go#L24) `func SetDebug(s bool)` -### func [SetDebugToolkit](/structs.go#L38) +### func [SetDebugChange](/debug.go#L52) + +`func SetDebugChange(s bool)` + +This passes the debugChange flag to the toolkit plugin + +### func [SetDebugToolkit](/debug.go#L37) `func SetDebugToolkit(s bool)` -### func [ShowDebugValues](/structs.go#L42) +This passes the debugToolkit flag to the toolkit plugin + +### func [ShowDebugValues](/debug.go#L66) `func ShowDebugValues()` -### func [StandardClose](/main.go#L128) +### func [StandardClose](/main.go#L119) `func StandardClose(n *Node)` The window is destroyed but the application does not quit -### func [StandardExit](/main.go#L135) +### func [StandardExit](/main.go#L125) `func StandardExit(n *Node)` The window is destroyed but the application does not quit -### func [Watchdog](/watchdog.go#L16) +### func [Watchdog](/watchdog.go#L15) `func Watchdog()` @@ -206,7 +233,13 @@ This goroutine can be used like a watchdog timer ## Types -### type [GuiConfig](/structs.go#L65) +### type [GuiArgs](/structs.go#L25) + +`type GuiArgs struct { ... }` + +This struct can be used with the go-arg package + +### type [GuiConfig](/structs.go#L30) `type GuiConfig struct { ... }` @@ -216,23 +249,14 @@ This goroutine can be used like a watchdog timer var Config GuiConfig ``` -### type [GuiDebug](/structs.go#L53) - -`type GuiDebug struct { ... }` - -This struct can be used with go-arg - -### type [Node](/structs.go#L84) +### type [Node](/structs.go#L48) `type Node struct { ... }` -The Node is simply the name and the size of whatever GUI element exists +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 -#### func [NewStandardWindow](/example_window_demo.go#L22) - -`func NewStandardWindow(title string) *Node` - -#### func [NewWindow](/window.go#L15) +#### func [NewWindow](/window.go#L14) `func NewWindow() *Node` @@ -280,7 +304,7 @@ func main() { You get a window ``` -### type [Symbol](/plugin.go#L17) +### type [Symbol](/plugin.go#L16) `type Symbol any` diff --git a/README.md b/README.md index 652787c..3ab8d30 100644 --- a/README.md +++ b/README.md @@ -87,12 +87,14 @@ hopefully also things like libSDL, faiface/pixel, slint ## References Useful links and other -external things -which might be useful +external things which might be useful * [Wikipedia Graphical widget](https://en.wikipedia.org/wiki/Graphical_widget) -* [Github mirror](https://github.com/witorg/gui) -* [Federated git pull](https://github.com/forgefed/forgefed) +* [GO Style Guide](https://google.github.io/styleguide/go/index) Code this way +* [MS Windows Application Library Kit](https://github.com/lxn/walk) +* [Federated git pull](https://github.com/forgefed/forgefed) Hopefully this will work for me with gitea +* [Github mirror](https://github.com/wit-go/gui) This repo on mirror. Hopefully I won't have to use this. +* [WIT GO projects](https://go.wit.org/) Attempt to model go.uber.org ## Functions diff --git a/andlabs.go b/andlabs.go index fac4a8b..95c1ad8 100644 --- a/andlabs.go +++ b/andlabs.go @@ -7,12 +7,10 @@ package gui import ( - "log" - "git.wit.org/wit/gui/toolkit/andlabs-direct" ) func trythis() { - log.Println("not sure what to try") + log(debugGui, "not sure what to try") toolkit.DebugToolkit = true } diff --git a/button.go b/button.go index c14988f..dd93721 100644 --- a/button.go +++ b/button.go @@ -1,23 +1,21 @@ package gui -import "log" - func (n *Node) NewButton(name string, custom func()) *Node { - newNode := n.New(name) + newNode := n.New(name, "Button") newNode.Widget.Custom = func() { - log.Println("even newer clicker() name", newNode.Widget) + log(debugGui, "even newer clicker() name", newNode.Widget) if (custom != nil) { custom() } else { - log.Println("wit/gui No callback function is defined for button name =", name) + log(debugGui, "wit/gui No callback function is defined for button name =", name) } } for _, aplug := range allPlugins { - log.Println("gui.NewButton() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewButton() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewButton == nil) { - log.Println("\tgui.NewButton() aplug.NewButton = nil", aplug.name) + log(debugGui, "\tgui.NewButton() aplug.NewButton = nil", aplug.name) continue } aplug.NewButton(&n.Widget, &newNode.Widget) diff --git a/checkbox.go b/checkbox.go index 0aa6aeb..0372a50 100644 --- a/checkbox.go +++ b/checkbox.go @@ -1,7 +1,5 @@ package gui -import "log" - func (n *Node) Checked() bool { n.Dump() return n.checked @@ -25,22 +23,29 @@ This was the old code func (n *Node) NewCheckbox(name string) *Node { - newNode := n.New(name) + newNode := n.New(name, "Checkbox") newNode.custom = n.custom newNode.Widget.Custom = func() { - log.Println("even newer clicker() name", newNode.Widget) + log(debugChange, "wit go gui checkbox", newNode.Widget) if (n.custom != nil) { + log(debugChange, "trying parent.custom() callback() name =", name) n.custom() } else { - log.Println("wit/gui No callback function is defined for button name =", name) + log(debugChange, "wit/gui No parent.custom() function is defined for button name =", name) + } + if (newNode.custom != nil) { + log(debugChange, "trying newNode.custom() callback name =", name) + newNode.custom() + } else { + log(debugChange, "wit/gui No newNode.custom() function is defined for button name =", name) } } for _, aplug := range allPlugins { - log.Println("gui.NewCheckbox() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewCheckbox() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewCheckbox == nil) { - log.Println("\tgui.NewCheckbox() aplug.NewCheckbox = nil", aplug.name) + log(debugGui, "\tgui.NewCheckbox() aplug.NewCheckbox = nil", aplug.name) continue } aplug.NewCheckbox(&n.Widget, &newNode.Widget) diff --git a/cmds/buttonplugin/main.go b/cmds/buttonplugin/main.go index cdd8ef3..6132ed6 100644 --- a/cmds/buttonplugin/main.go +++ b/cmds/buttonplugin/main.go @@ -21,7 +21,7 @@ func main() { // gui.LoadToolkit("default") // panic("WTF gocui not happening") // gui.LoadToolkit("gocui") - gui.Init() +// gui.Init() // buttonWindow() go gui.Main(func () { @@ -57,6 +57,10 @@ func buttonWindow() { w = gui.NewWindow() g = w.NewGroup("buttonGroup") + g.NewButton("hello", func () { + log.Println("world") + }) + g.NewButton("NewButton()", func () { log.Println("new foobar 2. Adding button 'foobar 3'") name := "foobar " + strconv.Itoa(counter) @@ -73,8 +77,12 @@ func buttonWindow() { g.NewGroup(name) }) - g.NewButton("hello", func () { - log.Println("world") + g.NewButton("gui.DebugWindow()", func () { + gui.DebugWindow() + }) + + g.NewButton("gui.GolangDebugWindow()", func () { + gui.GolangDebugWindow() }) g.NewButton("LoadToolkit(andlabs)", func () { @@ -86,7 +94,8 @@ func buttonWindow() { }) g.NewButton("Init()", func () { - gui.Init() + log.Println("gui.Init() is deprecated(?)") + //gui.Init() }) g.NewButton("Main()", func () { diff --git a/cmds/debug/main.go b/cmds/debug/main.go index c0df70b..375ccae 100644 --- a/cmds/debug/main.go +++ b/cmds/debug/main.go @@ -17,7 +17,7 @@ import ( func main() { log.Println("Starting my Control Panel") - gui.Init() +// gui.Init() // go gui.Main(helloworld) go gui.Main(gui.DebugWindow) // go gui.DemoToolkitWindow() diff --git a/cmds/helloworld/main.go b/cmds/helloworld/main.go index 43aa08c..5516340 100644 --- a/cmds/helloworld/main.go +++ b/cmds/helloworld/main.go @@ -7,7 +7,7 @@ import ( ) func main() { - gui.Init() + // gui.Init() gui.Main(helloworld) } diff --git a/cmds/textbox/Makefile b/cmds/textbox/Makefile index de22345..7b0e57d 100644 --- a/cmds/textbox/Makefile +++ b/cmds/textbox/Makefile @@ -1,5 +1,5 @@ run: build - ./textbox --guidebug + ./textbox --gui-debug build-release: go get -v -u -x . diff --git a/cmds/textbox/main.go b/cmds/textbox/main.go index b545d08..b260681 100644 --- a/cmds/textbox/main.go +++ b/cmds/textbox/main.go @@ -4,7 +4,6 @@ package main import ( "os" "log" - "fmt" "git.wit.org/wit/gui" arg "github.com/alexflint/go-arg" ) @@ -12,30 +11,20 @@ import ( type LogOptions struct { LogFile string Verbose bool - GuiDebug bool `help:"open up the wit/gui Debugging Window"` - GuiDemo bool `help:"open the wit/gui Demo Window"` + // GuiDebug bool `help:"open up the wit/gui Debugging Window"` + // GuiDemo bool `help:"open the wit/gui Demo Window"` User string `arg:"env:USER"` } var args struct { - Foo string - Bar bool LogOptions - gui.GuiDebug + gui.GuiArgs } - func main() { arg.MustParse(&args) - fmt.Println(args.Foo, args.Bar, args.User) - - gui.Config.Debug.Debug = args.Debug - /* - gui.Config.Debug.Change = args.DebugChange - gui.Config.Debug.Dump = args.DebugDump - gui.Config.Debug.Node = args.DebugNode - gui.Config.Debug.Tabs = args.DebugTabs - */ + // fmt.Println(args.Foo, args.Bar, args.User) + log.Println("Toolkit = ", args.Toolkit) /* f, err := os.OpenFile("/tmp/guilogfile", os.O_RDWR | os.O_CREATE | os.O_APPEND, 0666) @@ -48,14 +37,14 @@ func main() { log.Println("This is a test log entry") */ - gui.Init() + // gui.InitPlugins([]string{"andlabs"}) gui.Main(initGUI) } // This initializes the first window func initGUI() { var w *gui.Node - gui.Config.Title = "Hello World golang wit/gui Window" + gui.Config.Title = "Hello World" gui.Config.Width = 640 gui.Config.Height = 480 gui.Config.Exit = myDefaultExit @@ -65,16 +54,9 @@ func initGUI() { addDemoTab(w, "A Simple Tab Demo") addDemoTab(w, "A Second Tab") - /* - TODO: add these back - if (args.GuiDemo) { - gui.DemoToolkitWindow() - } - if (args.GuiDebug) { gui.DebugWindow() } - */ } func addDemoTab(window *gui.Node, title string) { diff --git a/common.go b/common.go index 5e2cd4d..5dc098d 100644 --- a/common.go +++ b/common.go @@ -1,21 +1,17 @@ package gui -import "log" // import "errors" import "regexp" // functions for handling text related GUI elements func (n *Node) SetText(str string) bool { - if (Config.Debug.Change) { - log.Println("gui.SetText() value =", str) - } - + log(debugChange, "gui.SetText() value = FIXME. NOT DOING ANYTHING", str) return true } func (n *Node) GetText() string { - return "not implemented" + return "TODO: GetText() = {}" } /* @@ -24,7 +20,7 @@ isAlpha := regexp.MustCompile(`^[A-Za-z]+$`).MatchString for _, username := range []string{"userone", "user2", "user-three"} { if !isAlpha(username) { - log.Printf("%q is not valid\n", username) + log(debugGui, "%q is not valid\n", username) } } @@ -44,35 +40,27 @@ func normalizeInt(s string) string { // reg, err := regexp.Compile("[^a-zA-Z0-9]+") reg, err := regexp.Compile("[^0-9]+") if err != nil { - log.Println("normalizeInt() regexp.Compile() ERROR =", err) + log(debugGui, "normalizeInt() regexp.Compile() ERROR =", err) return s } clean := reg.ReplaceAllString(s, "") - log.Println("normalizeInt() s =", clean) + log(debugGui, "normalizeInt() s =", clean) return clean } func commonCallback(n *Node) { // TODO: make all of this common code to all the widgets if (n.OnChanged == nil) { - if (Config.Debug.Change) { - log.Println("Not Running n.OnChanged(n) == nil") - } + log(debugChange, "Not Running n.OnChanged(n) == nil") } else { - if (Config.Debug.Change) { - log.Println("Running n.OnChanged(n)") - } + log(debugChange, "Running n.OnChanged(n)") n.OnChanged(n) } if (n.custom == nil) { - if (Config.Debug.Change) { - log.Println("Not Running n.custom(n) == nil") - } + log(debugChange, "Not Running n.custom(n) == nil") } else { - if (Config.Debug.Change) { - log.Println("Running n.custom()") - } + log(debugChange, "Running n.custom()") n.custom() } } diff --git a/debian/Makefile b/debian/Makefile new file mode 100644 index 0000000..0b81eba --- /dev/null +++ b/debian/Makefile @@ -0,0 +1,49 @@ +# GITVERSION=$(shell git rev-parse FETCH_HEAD) +VERSION=$(shell git describe --tags $(git rev-list --tags --max-count=1) | sed 's/^v//') + +BASENAME=go-wit-gui + +all: help deb + +help: + @echo + @echo "make deb # attempt to build the .deb package using dpkg" + @echo + +deb: clean extract DEBIAN build + +clean: + rm -rf ../files + rm -f ../*.deb + rm -f ../*.tar.xz data.tar.xz + rm -rf DEBIAN + +extract: + mkdir -p ../files/usr/lib/go-gui + cp ../toolkit/*.so ../files/usr/lib/go-gui/ + cp ../README.md ../files/usr/lib/go-gui/ + cp ../cmds/textbox/textbox ../files/usr/lib/go-gui/textbox-demo + +# makes the DEBIAN/ directory +DEBIAN: + mkdir -p DEBIAN + + # make the md5sum file + cd ../files/ && find -type f -exec md5sum '{}' \; |sort -k2 >../md5sums + mv ../md5sums DEBIAN/ + + # make the control there + mkdir -p DEBIAN + cp control DEBIAN/ + echo Version: ${VERSION} >>DEBIAN/control + + cp postinst DEBIAN + +build: + mv DEBIAN ../files/ + cd .. && dpkg-deb --build files ${BASENAME}_${VERSION}_amd64.deb + @echo + @echo '#######################' + cd .. && dpkg-deb --info ${BASENAME}_${VERSION}_amd64.deb + @echo '#######################' + @echo diff --git a/debian/compat b/debian/compat new file mode 100644 index 0000000..f599e28 --- /dev/null +++ b/debian/compat @@ -0,0 +1 @@ +10 diff --git a/debian/control b/debian/control new file mode 100644 index 0000000..906f089 --- /dev/null +++ b/debian/control @@ -0,0 +1,9 @@ +Source: go-wit-gui +Build-Depends: golang +Package: go-wit-gui +Maintainer: Jeff Carr +Architecture: amd64 +Depends: +Recommends: libgtk-3-0 +Description: a abstraction layer for Go visual elements (GTK, QT, etc) + Package gui implements a abstraction layer for Go visual elements. diff --git a/debian/postinst b/debian/postinst new file mode 100755 index 0000000..1a24852 --- /dev/null +++ b/debian/postinst @@ -0,0 +1 @@ +#!/bin/sh diff --git a/debug.go b/debug.go new file mode 100644 index 0000000..f2be829 --- /dev/null +++ b/debug.go @@ -0,0 +1,184 @@ +package gui + +// Lots of debugging things: +// A function dump out the binary tree + +import ( + // "fmt" + "reflect" +) + +// various debugging flags +var debugGui bool = false +var debugDump bool = false +var debugNode bool = false +var debugTabs bool = false +var debugChange bool = false // shows user events like mouse and keyboard +var debugPlugin bool = false +var debugToolkit bool = false + +func GetDebug () bool { + return debugGui +} + +func SetDebug (s bool) { + debugGui = s + // debugDump = s + // debugNode = s +} + +/* +func GetDebugToolkit () bool { + return debugToolkit +} +*/ + +// This passes the debugToolkit flag to the toolkit plugin +func SetDebugToolkit (s bool) { + debugToolkit = s + for _, aplug := range allPlugins { + log(debugPlugin, "gui.SetDebugToolkit() aplug =", aplug.name) + if (aplug.SetDebugToolkit == nil) { + log(debugPlugin, "\tgui.SetDebugToolkit() = nil", aplug.name) + continue + } + aplug.SetDebugToolkit(s) + return + } + log(debugPlugin, "\tgui.SetDebugToolkit() = nil in all plugins") +} + +// This passes the debugChange flag to the toolkit plugin +func SetDebugChange (s bool) { + // debugToolkit = s + for _, aplug := range allPlugins { + log(debugPlugin, "gui.SetDebugChange() aplug =", aplug.name) + if (aplug.SetDebugChange == nil) { + log(debugPlugin, "\tgui.SetDebugChange() = nil", aplug.name) + continue + } + aplug.SetDebugChange(s) + return + } + log(debugPlugin, "\tgui.SetDebugChange() = nil in all plugins") +} + +func ShowDebugValues() { + log(true, "Debug =", debugGui) + log(true, "DebugDump =", debugDump) + log(true, "DebugNode =", debugNode) + log(true, "DebugTabs =", debugTabs) + log(true, "DebugPlugin =", debugPlugin) + log(true, "DebugChange =", debugChange) + log(true, "DebugToolkit =", debugToolkit) + + // dump out the debugging flags for the plugins + for _, aplug := range allPlugins { + log(debugPlugin, "gui.ShowDebug() aplug =", aplug.name) + if (aplug.ShowDebug == nil) { + log(debugPlugin, "\tgui.ShowDebug() = nil", aplug.name) + continue + } + aplug.ShowDebug() + return + } +} + +func (n *Node) Dump() { + if ! debugDump { + return + } + Indent("NODE DUMP START") + Indent("id = ", n.id) + Indent("Name = ", n.Name) + Indent("Width = ", n.Width) + Indent("Height = ", n.Height) + + if (n.parent == nil) { + Indent("parent = nil") + } else { + Indent("parent.id =", n.parent.id) + } + if (n.children != nil) { + Indent("children = ", n.children) + } + if (n.custom != nil) { + Indent("custom = ", n.custom) + } + Indent("checked = ", n.checked) + if (n.OnChanged != nil) { + Indent("OnChanged = ", n.OnChanged) + } + Indent("text = ", reflect.ValueOf(n.text).Kind(), n.text) + Indent("NODE DUMP END") +} + +var listChildrenParent *Node +var listChildrenDepth int = 0 +var defaultPadding = " " + +func Indent(a ...interface{}) { + logindent(listChildrenDepth, defaultPadding, a...) +} + +func (n *Node) dumpWidget() { + var info string + + if (n.Widget.Type == "") { + n.Widget.Type = "UNDEF" + } + info = n.Widget.Type + + info += ", " + n.Widget.Name + if (n.Name != n.Widget.Name) { + info += " NAME MISMATCH" + } + + logindent(listChildrenDepth, defaultPadding, n.id, info) +} + +func (n *Node) ListChildren(dump bool) { + n.dumpWidget() + + if (dump == true) { + n.Dump() + } + if len(n.children) == 0 { + if (n.parent == nil) { + } else { + log(debugNode, "\t\t\tparent =",n.parent.id) + if (listChildrenParent != nil) { + log(debugNode, "\t\t\tlistChildrenParent =",listChildrenParent.id) + if (listChildrenParent.id != n.parent.id) { + // log("parent.child does not match child.parent") + exit("parent.child does not match child.parent") + } + } + } + log(debugNode, "\t\t", n.id, "has no children") + return + } + for _, child := range n.children { + if (child.parent != nil) { + log(debugNode, "\t\t\tparent =",child.parent.id) + } else { + log(debugGui, "\t\t\tno parent") + // memory corruption? non-threadsafe access? + // can all binary tree changes to Node.parent & Node.child be forced into a singular goroutine? + panic("something is wrong with the wit golang gui logic and the binary tree is broken. child has no parent") + } + if (dump == true) { + child.Dump() + } + if (child.children == nil) { + log(debugNode, "\t\t", child.id, "has no children") + } else { + log(debugNode, "\t\t\tHas children:", child.children) + } + listChildrenParent = n + listChildrenDepth += 1 + child.ListChildren(dump) + listChildrenDepth -= 1 + } + return +} diff --git a/debug_window.go b/debug_window.go new file mode 100644 index 0000000..82d7557 --- /dev/null +++ b/debug_window.go @@ -0,0 +1,194 @@ +package gui + +var bugWin *Node +var mapWindows map[string]*Node + +/* + Creates a window helpful for debugging this package +*/ +func DebugWindow() { + Config.Title = "go.wit.org/gui debug window" + Config.Width = 300 + Config.Height = 200 + Config.Exit = StandardClose + bugWin = NewWindow() + bugWin.DebugTab("Debug Tab") +} + +var checkd, checkdn, checkdt, checkdtk *Node + +//////////////////////// debug flags ////////////////////////////////// +func debugFlags(n *Node) { + var df, checkdn, checkdd, changeCheckbox *Node + df = n.NewGroup("Debug Flags") + df.NewLabel("flags to control debugging output") + + cb := df.NewCheckbox("debugGui") + cb.custom = func() { + log(true, "custom ran correctly for =", n.Name) + debugGui = true + } + + checkdd = df.NewCheckbox("debugDump") + checkdd.custom = func() { + log(true, "debugDump() custom ran correctly for =", n.Name) + debugDump = true + } + + checkdn = df.NewCheckbox("debugNode") + checkdn.custom = func() { + log(true, "debugNode() custom ran correctly for =", n.Name) + debugNode = true + } + + + cb = df.NewCheckbox("debugChange") + cb.custom = func() { + log(true, "checkbox: custom() ran correctly for =", cb.Name) + log(true, "START debugChange =", debugChange) + if (debugChange) { + debugChange = false + SetDebugChange(false) + log(true, "debugToolkitChange turned off node.Name =", cb.Name) + } else { + debugChange = true + SetDebugChange(true) + log(true, "debugToolkitChange turned on Name =", cb.Name) + } + log(true, "END debugChange =", debugChange) + } + + cb = df.NewCheckbox("debugTabs") + cb.custom = func() { + log(true, "debugTabs() custom ran correctly for =", n.Name) + debugTabs = true + } + + cb = df.NewCheckbox("debugPlugin") + cb.custom = func() { + log(true, "debugPlugin() custom ran correctly for =", n.Name) + debugPlugin = true + } + + changeCheckbox = df.NewCheckbox("debugToolkit") + changeCheckbox.custom = func() { + SetDebugToolkit(true) + } + + df.NewButton("Debug Toolkit", func() { + if (debugToolkit) { + SetDebugToolkit(false) + log(true, "debugToolkit turned off node.Name =", n.Name) + } else { + SetDebugToolkit(true) + log(true, "debugToolkit turned on Name =", n.Name) + } + }) + + df.NewButton("Dump Debug Flags", func () { + ShowDebugValues() + }) +} + +func (n *Node) DebugTab(title string) *Node { + var newN, gog, g1, g2, g3, dd *Node + + // time.Sleep(1 * time.Second) + newN = n.NewTab(title) + newN.Dump() + +//////////////////////// main debug things ////////////////////////////////// + gog = newN.NewGroup("GOLANG") + gog.NewLabel("go language") + gog.NewButton("GO Language Debug", func () { + GolangDebugWindow() + }) + + gog.NewLabel("wit/gui package") + gog.NewButton("Demo toolkit andlabs/ui", func () { + // DemoToolkitWindow() + }) + + debugFlags(newN) + +//////////////////////// window debugging things ////////////////////////////////// + g1 = newN.NewGroup("Current Windows") + dd = g1.NewDropdown("Window Dropdown") + log(debugGui, "dd =", dd) + + // initialize the windows map if it hasn't been + if (mapWindows == nil) { + mapWindows = make(map[string]*Node) + } + + var dump = false + for _, child := range Config.master.children { + log(debugGui, "\t\t", child.id, child.Width, child.Height, child.Name) + if (child.parent != nil) { + log(debugGui, "\t\t\tparent =",child.parent.id) + } else { + log(debugGui, "\t\t\tno parent") + panic("no parent") + } + if (dump == true) { + child.Dump() + } + dd.AddDropdownName(child.Name) + mapWindows[child.Name] = child + } + + dd.SetDropdown(0) + + g2 = newN.NewGroup("Debug Window") + g2.NewButton("SetMargined(tab)", func () { + log(debugChange, "START SetMargined(tab)", g2.Name) + // name := dd.GetText() + name := dd.Widget.S + log(debugChange, "name =", name) + log(debugChange, "mapWindows[name] =", mapWindows[name]) + /* + for s, n := range mapWindows { + log(debugChange, "\tname =", name) + log(debugChange, "\tmapWindows s =", s) + log(debugChange, "\tmapWindows[s] =", n) + } + */ + bugWin = mapWindows[name] + log(debugChange, "END dd.Widget.S =", dd.Widget.S) + // gw.UiTab.SetMargined(*gw.TabNumber, true) + }) + g2.NewButton("Hide(tab)", func () { + log(debugChange, "\tclick() START", g2.Name) + // gw.UiTab.Hide() + }) + g2.NewButton("Show(tab)", func () { + // gw.UiTab.Show() + }) + g2.NewButton("Delete(tab)", func () { + // gw.UiTab.Delete(*gw.TabNumber) + }) + g2.NewButton("change Title", func () { + // mainWindow.SetText("hello world") + }) + + ///////////////////////////////////////////////////// + g3 = newN.NewGroup("Node Debug") + + g3.NewButton("Node.Dump()", func () { + debugGui = true + debugDump = true + bugWin.Dump() + }) + g3.NewButton("Node.ListChildren(false)", func () { + debugGui = true + debugDump = true + bugWin.ListChildren(false) + }) + g3.NewButton("Node.ListChildren(true)", func () { + debugGui = true + debugDump = true + bugWin.ListChildren(true) + }) + + return newN +} diff --git a/doc.go b/doc.go index 344ba79..29f36db 100644 --- a/doc.go +++ b/doc.go @@ -84,16 +84,17 @@ Bugs References Useful links and other -external things -which might be useful +external things which might be useful [Wikipedia Graphical widget]: https://en.wikipedia.org/wiki/Graphical_widget [Github mirror]: https://github.com/witorg/gui [Federated git pull]: https://github.com/forgefed/forgefed +[GO Style Guide]: https://google.github.io/styleguide/go/index * [Wikipedia Graphical widget] * [Github mirror] * [Federated git pull] + * [GO Style Guide] */ diff --git a/dropdown.go b/dropdown.go index f500c55..e999f7e 100644 --- a/dropdown.go +++ b/dropdown.go @@ -1,31 +1,53 @@ package gui -import "log" - func (n *Node) AddDropdownName(name string) { for _, aplug := range allPlugins { - log.Println("gui.AddDropdownName() aplug =", aplug.name, "name =", name) + log(debugGui, "gui.AddDropdownName() aplug =", aplug.name, "name =", name) if (aplug.AddDropdownName == nil) { - log.Println("\tgui.AddDropdownName() aplug.NewDropdown = nil", aplug.name) + log(debugGui, "\tgui.AddDropdownName() aplug.NewDropdown = nil", aplug.name) continue } aplug.AddDropdownName(&n.Widget, name) } + + if (n.Widget.Custom == nil) { + n.SetDropdownChange( func() { + log(debugChange, "gui.Dropdown change() REAL Custom() name =", name) + log(debugChange, "gui.Dropdown change() REAL n.Widget.S =", n.Widget.S) + }) + } + // TODO, this makes functions over and over for each dropdown menu + /* + n.Widget.Custom = func() { + log(debugChange, "gui.Dropdown change() START Custom() name =", name) + log(debugChange, "gui.Dropdown change() START n.Widget.S =", n.Widget.S) + } + */ } -func (n *Node) SetDropdown(i int) { +func (n *Node) SetDropdown(s any) { + log(debugGui, "gui.SetDropdown() TODO: make this work. s =", s) } -func (n *Node) NewDropdown(text string) *Node { - newNode := n.New(text) +func (n *Node) SetDropdownChange(f func()) { + n.Widget.Custom = f +} + +func (n *Node) NewDropdown(name string) *Node { + newNode := n.New(name, "Dropdown") for _, aplug := range allPlugins { - log.Println("gui.NewDropdown() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewDropdown() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewDropdown == nil) { - log.Println("\tgui.NewDropdown() aplug.NewDropdown = nil", aplug.name) + log(debugGui, "\tgui.NewDropdown() aplug.NewDropdown = nil", aplug.name) continue } aplug.NewDropdown(&n.Widget, &newNode.Widget) } + + // TODO, this doesn't work for some reason (over-written by plugin?) + newNode.Widget.Custom = func() { + log(true, "gui.NewDropdown() START Custom()") + } return newNode } diff --git a/example_window_debug.go b/example_window_debug.go deleted file mode 100644 index 0c6503e..0000000 --- a/example_window_debug.go +++ /dev/null @@ -1,163 +0,0 @@ -package gui - -import ( - "log" -) - -var names = make([]string, 100) -var nodeNames = make([]string, 100) - -var bugWin *Node -/* - Creates a window helpful for debugging this package -*/ -func DebugWindow() { - Config.Title = "git.wit.org/wit/gui debug fixme" - Config.Width = 300 - Config.Height = 200 - Config.Exit = StandardClose - bugWin = NewWindow() - bugWin.DebugTab("WIT GUI Debug Tab") -} - -// this function is used by the examples to add a tab -// dynamically to the bugWin node -// TODO: make this smarter once this uses toolkit/ -func DebugTab() { - if (bugWin == nil) { - log.Println("Not sure what window to add this to? Use node.DebugTab() instead") - return; - } - bugWin.DebugTab("does this work?") -} - -var checkd, checkdn, checkdt, checkdtk *Node - -//////////////////////// debug flags ////////////////////////////////// -func debugFlags(n *Node) { - var df, checkd, checkdn, checkdd, changeCheckbox *Node - df = n.NewGroup("Debug Flags") - df.NewLabel("flags to control debugging output") - - checkd = df.NewCheckbox("Debug") - checkd.OnChanged = func(*Node) { - // checkd.checked = checkd.toolkit.Checked() - Config.Debug.Debug = true - if (Config.Debug.Debug) { - log.Println("Debug turned on") - } else { - log.Println("Debug turned off") - } - } - - checkdn = df.NewCheckbox("Debug Node") - checkdn.OnChanged = func(*Node) { - Config.Debug.Node = true - } - - checkdd = df.NewCheckbox("Debug node.Dump()") - checkdd.OnChanged = func(*Node) { - Config.Debug.Dump = true - } - - changeCheckbox = df.NewCheckbox("Debug Change") - changeCheckbox.OnChanged = func(*Node) { - Config.Debug.Change = true - } - - df.NewButton("Dump Debug Flags", func () { - ShowDebugValues() - }) - -} - -func (n *Node) DebugTab(title string) *Node { - var newN, gog, g1, g2, g3, dd *Node - - // time.Sleep(1 * time.Second) - newN = n.NewTab(title) - newN.Dump() - -//////////////////////// main debug things ////////////////////////////////// - gog = newN.NewGroup("GOLANG") - gog.NewLabel("go language") - gog.NewButton("GO Language Debug", func () { - // GolangDebugWindow() - }) - - gog.NewLabel("wit/gui package") - gog.NewButton("WIT/GUI Package Debug", func () { - Config.Width = 640 - Config.Height = 480 - // Queue(DebugWindow) - }) - gog.NewButton("Demo wit/gui", func () { - // DemoWindow() - }) - gog.NewButton("Demo toolkit andlabs/ui", func () { - // DemoToolkitWindow() - }) - - debugFlags(newN) - -//////////////////////// window debugging things ////////////////////////////////// - g1 = newN.NewGroup("Current Windows") - dd = g1.NewDropdown("Window Dropdown") - log.Println("dd =", dd) - - var dump = false - for _, child := range Config.master.children { - log.Println("\t\t", child.id, child.Width, child.Height, child.Name) - if (child.parent != nil) { - log.Println("\t\t\tparent =",child.parent.id) - } else { - log.Println("\t\t\tno parent") - panic("no parent") - } - if (dump == true) { - child.Dump() - } - dd.AddDropdownName(child.Name) - } - dd.SetDropdown(0) - - g2 = newN.NewGroup("Debug Window") - g2.NewButton("SetMargined(tab)", func () { - log.Println("\tSTART") - name := dd.GetText() - log.Println("\tENDed with", name) - // gw.UiTab.SetMargined(*gw.TabNumber, true) - }) - g2.NewButton("Hide(tab)", func () { - // gw.UiTab.Hide() - }) - g2.NewButton("Show(tab)", func () { - // gw.UiTab.Show() - }) - g2.NewButton("Delete(tab)", func () { - // gw.UiTab.Delete(*gw.TabNumber) - }) - g2.NewButton("change Title", func () { - // mainWindow.SetText("hello world") - }) - - ///////////////////////////////////////////////////// - g3 = newN.NewGroup("Node Debug") - - g3.NewButton("Node.Dump()", func () { - bugWin.Dump() - }) - g3.NewButton("Node.ListChildren(false)", func () { - bugWin.ListChildren(false) - }) - g3.NewButton("Node.ListChildren(true)", func () { - bugWin.ListChildren(true) - }) - g3.NewButton("AddDebugTab()", func () { - if (bugWin != nil) { - bugWin.DebugTab("added this DebugTab") - } - }) - - return newN -} diff --git a/example_window_demo.go b/example_window_demo.go deleted file mode 100644 index be07496..0000000 --- a/example_window_demo.go +++ /dev/null @@ -1,30 +0,0 @@ -package gui - -import "log" -// import "time" -// import toolkit "git.wit.org/wit/gui/toolkit/andlabs" - -// -// This creates a window that shows how this package works -// -func DemoWindow() { - var w, t1 *Node - log.Println("DemoWindow() START") - - w = NewStandardWindow("Demo of WIT/GUI") - - t1 = w.DebugTab("WIT GUI Debug Tab t1") - t1.DebugTab("WIT GUI Debug Tab t2") - - log.Println("DemoWindow() END") -} - -func NewStandardWindow(title string) *Node { - log.Println("NewStandardWindow() creating", title) - - Config.Title = title - Config.Width = 640 - Config.Height = 480 - Config.Exit = StandardClose - return NewWindow() -} diff --git a/example_window_golang_debug.go b/example_window_golang_debug.go index 464ab09..466654a 100644 --- a/example_window_golang_debug.go +++ b/example_window_golang_debug.go @@ -1,7 +1,5 @@ package gui -import "log" - import ( "os" "runtime" @@ -19,88 +17,88 @@ func GolangDebugWindow() { w = NewWindow() t = w.NewTab("Debug Tab") - log.Println("debugWindow() START") + log("debugWindow() START") /////////////////////////////// Column DEBUG GOLANG ////////////////////// g := t.NewGroup("GO Language") g.NewButton("runtime.Stack()", func () { - log.Println("\tSTART") + log("\tSTART") buf := make([]byte, 1<<16) runtime.Stack(buf, true) - log.Printf("%s", buf) - log.Println("\tEND") + log("\t %s", buf) + log("\tEND") }) g.NewButton("dumpModuleInfo()", func () { - log.Println("\tSTART") + log("\tSTART") dumpModuleInfo() - log.Println("\tEND") + log("\tEND") }) g.NewButton("debug.PrintStack()", func () { - log.Println("\tSTART") + log("\tSTART") debug.PrintStack() - log.Println("\tEND") + log("\tEND") }) g.NewButton("pprof.Lookup(goroutine)", func () { - log.Println("\tSTART") + log("\tSTART") pprof.Lookup("goroutine").WriteTo(os.Stdout, 1) - log.Println("\tEND") + log("\tEND") }) g.NewButton("pprof.Lookup(heap)", func () { - log.Println("\tSTART") + log("\tSTART") pprof.Lookup("heap").WriteTo(os.Stdout, 1) - log.Println("\tEND") + log("\tEND") }) g.NewButton("pprof.Lookup(block)", func () { - log.Println("\tSTART") + log("\tSTART") pprof.Lookup("block").WriteTo(os.Stdout, 1) - log.Println("\tEND") + log("\tEND") }) g.NewButton("pprof.Lookup threadcreate", func () { - log.Println("\tSTART") + log("\tSTART") pprof.Lookup("threadcreate").WriteTo(os.Stdout, 1) - log.Println("\tEND") + log("\tEND") }) g.NewButton("runtime.ReadMemStats", func () { var s runtime.MemStats runtime.ReadMemStats(&s) - log.Printf("alloc: %v bytes\n", s.Alloc) - log.Printf("total-alloc: %v bytes\n", s.TotalAlloc) - log.Printf("sys: %v bytes\n", s.Sys) - log.Printf("lookups: %v\n", s.Lookups) - log.Printf("mallocs: %v\n", s.Mallocs) - log.Printf("frees: %v\n", s.Frees) - log.Printf("heap-alloc: %v bytes\n", s.HeapAlloc) - log.Printf("heap-sys: %v bytes\n", s.HeapSys) - log.Printf("heap-idle: %v bytes\n", s.HeapIdle) - log.Printf("heap-in-use: %v bytes\n", s.HeapInuse) - log.Printf("heap-released: %v bytes\n", s.HeapReleased) - log.Printf("heap-objects: %v\n", s.HeapObjects) - log.Printf("stack-in-use: %v bytes\n", s.StackInuse) - log.Printf("stack-sys: %v bytes\n", s.StackSys) - log.Printf("next-gc: when heap-alloc >= %v bytes\n", s.NextGC) - log.Printf("last-gc: %v ns\n", s.LastGC) - log.Printf("gc-pause: %v ns\n", s.PauseTotalNs) - log.Printf("num-gc: %v\n", s.NumGC) - log.Printf("enable-gc: %v\n", s.EnableGC) - log.Printf("debug-gc: %v\n", s.DebugGC) + log("alloc: %v bytes\n", s.Alloc) + log("total-alloc: %v bytes\n", s.TotalAlloc) + log("sys: %v bytes\n", s.Sys) + log("lookups: %v\n", s.Lookups) + log("mallocs: %v\n", s.Mallocs) + log("frees: %v\n", s.Frees) + log("heap-alloc: %v bytes\n", s.HeapAlloc) + log("heap-sys: %v bytes\n", s.HeapSys) + log("heap-idle: %v bytes\n", s.HeapIdle) + log("heap-in-use: %v bytes\n", s.HeapInuse) + log("heap-released: %v bytes\n", s.HeapReleased) + log("heap-objects: %v\n", s.HeapObjects) + log("stack-in-use: %v bytes\n", s.StackInuse) + log("stack-sys: %v bytes\n", s.StackSys) + log("next-gc: when heap-alloc >= %v bytes\n", s.NextGC) + log("last-gc: %v ns\n", s.LastGC) + log("gc-pause: %v ns\n", s.PauseTotalNs) + log("num-gc: %v\n", s.NumGC) + log("enable-gc: %v\n", s.EnableGC) + log("debug-gc: %v\n", s.DebugGC) }) } func dumpModuleInfo() { tmp, _ := debug.ReadBuildInfo() if tmp == nil { - log.Println("This wasn't compiled with go module support") + log("This wasn't compiled with go module support") return } - log.Println("mod.Path = ", tmp.Path) - log.Println("mod.Main.Path = ", tmp.Main.Path) - log.Println("mod.Main.Version = ", tmp.Main.Version) - log.Println("mod.Main.Sum = ", tmp.Main.Sum) + log("mod.Path = ", tmp.Path) + log("mod.Main.Path = ", tmp.Main.Path) + log("mod.Main.Version = ", tmp.Main.Version) + log("mod.Main.Sum = ", tmp.Main.Sum) for _, value := range tmp.Deps { - log.Println("\tmod.Path = ", value.Path) - log.Println("\tmod.Version = ", value.Version) + log("\tmod.Path = ", value.Path) + log("\tmod.Version = ", value.Version) } } diff --git a/group.go b/group.go index a0fbe60..2037861 100644 --- a/group.go +++ b/group.go @@ -1,21 +1,17 @@ package gui -import "log" - // TODO: which name is better. AddGroup or NewGroup ? // first reaction is NewGroup func (n *Node) NewGroup(name string) *Node { var newNode *Node + newNode = n.New(name, "Group") - if (GetDebug()) { - log.Println("toolkit.NewGroup() START", name) - } + log(debugGui, "toolkit.NewGroup() START", name) - newNode = n.New(name) - log.Println("gui.Node.NewGroup()", name) + log(debugGui, "gui.Node.NewGroup()", name) for _, aplug := range allPlugins { - log.Println("gui.Node.NewGroup() toolkit plugin =", aplug.name) + log(debugGui, "gui.Node.NewGroup() toolkit plugin =", aplug.name) if (aplug.NewGroup == nil) { continue } diff --git a/int.go b/int.go index da27092..a7880dc 100644 --- a/int.go +++ b/int.go @@ -1,8 +1,7 @@ package gui -import "log" +// import "github.com/davecgh/go-spew/spew" -import "github.com/davecgh/go-spew/spew" /* Get the int from the gui toolkit @@ -14,12 +13,10 @@ import "github.com/davecgh/go-spew/spew" Is it "has to go" or "should go"? Probably it makes sense to strictly inforce it. No "callback" functions. IPC only (go channels) */ func (n *Node) Int() int { - if (Config.Debug.Toolkit) { - log.Println("gui.Node.Int() for node name =", n.Name) - scs := spew.ConfigState{MaxDepth: 1} - scs.Dump(n) - } + log(debugToolkit, "gui.Node.Int() for node name =", n.Name) + log(debugToolkit, SPEW, n) + // FIXME: this needs to be redone // i := n.toolkit.Value() i := 3333 return i @@ -31,7 +28,8 @@ func (n *Node) Value() int { } func (n *Node) SetValue(i int) { - log.Println("gui.SetValue() START") + log(debugGui, "gui.SetValue() START") n.Dump() + // FIXME: this needs to be redone // n.toolkit.SetValue(i) } diff --git a/label.go b/label.go index 6542a68..f51ce66 100644 --- a/label.go +++ b/label.go @@ -1,16 +1,15 @@ package gui -import "log" // import "errors" // import "regexp" func (n *Node) NewLabel(text string) *Node { - newNode := n.New(text) + newNode := n.New(text, "Label") for _, aplug := range allPlugins { - log.Println("gui.NewLabel() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewLabel() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewLabel == nil) { - log.Println("\tgui.NewLabel() aplug.NewLabel = nil", aplug.name) + log(debugGui, "\tgui.NewLabel() aplug.NewLabel = nil", aplug.name) continue } aplug.NewLabel(&n.Widget, &newNode.Widget) diff --git a/log.go b/log.go new file mode 100644 index 0000000..71e22f6 --- /dev/null +++ b/log.go @@ -0,0 +1,137 @@ +// +// version v1.3 +// +// I like things to be easy. +// +// this means all the log settings are in one place. it should allow +// things to be over-ridden externally to the library +// but still allow command line --args to pass debugging settings +// +// I also have a generic sleep() and exit() in here because it's simple +// +// Usage: +// +// log("something", foo, bar) +// var DEBUG bool = true +// log(DEBUG, "something else", someOtherVariable) # if DEBUG == false, return doing nothing +// log(SPEW, "something else", someOtherVariable) # this get's sent to spew.Dump(). Very useful for debugging! +// +package gui + +import ( + "os" + "runtime" + "runtime/pprof" + golog "log" + "time" + "reflect" + "github.com/davecgh/go-spew/spew" + // "net" +) + +var LOGOFF bool = false // turn this off, all logging stops +var WARN bool +var INFO bool + +type spewt struct { + a bool +} + +var SPEW spewt + + +/* + sleep() # you know what this does? sleeps for 1 second. yep. dump. easy. + sleep(.1) # you know what this does? yes, it sleeps for 1/10th of a second +*/ +func sleep(a ...any) { + if (a == nil) { + time.Sleep(time.Second) + return + } + + log("sleep", a[0]) + + switch a[0].(type) { + case int: + time.Sleep(time.Duration(a[0].(int)) * time.Second) + case float64: + time.Sleep(time.Duration(a[0].(float64) * 1000) * time.Millisecond) + default: + log("sleep a[0], type = ", a[0], reflect.TypeOf(a[0])) + } +} + +/* + exit() # yep. exits. I guess everything must be fine + exit(3) # I guess 3 it is then + exit("dont like apples") # ok. I'll make a note of that +*/ +func exit(a ...any) { + log("exit", a) + //if (a) { + // os.Exit(a) + //} + os.Exit(0) +} + +/* + I've spent, am spending, too much time thinking about 'logging'. 'log', 'logrus', 'zap', whatever. + I'm not twitter. i don't give a fuck about how many nanoseconds it takes to log. Anyway, this + implementation is probably faster than all of those because you just set one bool to FALSE + and it all stops. + Sometimes I need to capture to stdout, sometimes stdout can't + work because it doesn't exist for the user. This whole thing is a PITA. Then it's spread + over 8 million references in every .go file. I'm tapping out and putting + it in one place. here it is. Also, this makes having debug levels really fucking easy. + You can define whatever level of logging you want from anywhere (command line) etc. + + log() # doesn't do anything + log(stuff) # sends it to whatever log you define in a single place. here is the place +*/ + +func log(a ...any) { + if (LOGOFF) { + return + } + + if (a == nil) { + return + } + var blah bool + if (reflect.TypeOf(a[0]) == reflect.TypeOf(blah)) { + // golog.Println("\t a[0] = bool") + if (a[0] == false) { + return + } + a[0] = "WIT/GUI" + } + + if (reflect.TypeOf(a[0]) == reflect.TypeOf(SPEW)) { + a = a[1:] + spew.Dump(a) + return + } + + golog.Println(a...) +} + +func loggo() { + pprof.Lookup("goroutine").WriteTo(os.Stdout, 1) + golog.Println("runtime.NumGoroutine() = ", runtime.NumGoroutine()) +} + +func logindent(depth int, format string, a ...any) { + var tabs string + for i := 0; i < depth; i++ { + tabs = tabs + format + } + + // newFormat := tabs + strconv.Itoa(depth) + " " + format + newFormat := tabs + format + + // array prepend(). Why isn't this a standard function. It should be: + // a.prepend(debugGui, newFormat) + a = append([]any{debugGui, newFormat}, a...) + log(a...) +} diff --git a/main.go b/main.go index 159b84e..01e15b6 100644 --- a/main.go +++ b/main.go @@ -1,8 +1,6 @@ package gui import ( - "log" - "os" "embed" ) @@ -18,83 +16,76 @@ const Yaxis = 1 // stack things vertically var res embed.FS func init() { - log.Println("gui.init() has been run") + debugGui = true + log(debugGui, "gui.init() has been run") Config.counter = 0 Config.prefix = "wit" - // Config.Debug.Debug = true - // Config.Debug.Node = true - // Config.Debug.Tabs = true - title := "guiBinaryTree" w := 640 h := 480 // Populates the top of the binary tree Config.master = addNode(title, w, h) - if (Config.Debug.Debug) { - Config.master.Dump() - } + // Config.master.Dump() + debugGui = false } -func Init() { - var initBAD bool = true +func InitPlugins(names []string) { + log(debugGui, "Starting gui.Init()") - if (Config.Debug.Debug) { - log.Println("Starting gui.Init()") - } for _, aplug := range allPlugins { - log.Println("gui.LoadToolkit() already loaded toolkit plugin =", aplug.name) - initBAD = false + log(debugGui, "gui.LoadToolkit() already loaded toolkit plugin =", aplug.name) + for _, name := range names { + if (name == aplug.name) { + return + } + } + } + + // try to load each plugin in the order passed to this function + for _, name := range names { + if (LoadToolkit(name)) { + // aplug.InitOk = true + // aplug.Init() + return + } } // the program didn't specify a plugin. Try to load one // TODO: detect the OS & user preferences to load the best one - if (initBAD) { - if (LoadToolkit("andlabs")) { - initBAD = false - } + // TODO: commented out Init() on 02/26/2023 because I'm not sure how to run it correctly + if (LoadToolkit("andlabs")) { + // aplug.InitOk = true + // aplug.Init() + return } - // andlabs gui plugin failed. fall back to the terminal gui (should be compiled into the binary) - if (initBAD) { - if (LoadToolkit("gocui")) { - initBAD = false - } + if (LoadToolkit("gocui")) { + // aplug.InitOk = true + // aplug.Init() + return } - // locate the shared library file - // panic("WTF Init()") - for _, aplug := range allPlugins { - log.Println("gui.Node.Init() toolkit plugin =", aplug.name) - if (aplug.InitOk) { - log.Println("gui.Node.Init() Already Ran Init()", aplug.name) - continue - } - if (aplug.Init == nil) { - log.Println("gui.Node.Main() Init == nil", aplug.name) - continue - } - aplug.InitOk = true - aplug.Init() - } - // StandardExit(nil) + // Should die here? TODO: need a Node to call StandardExit + // StandardExit("golang wit/gui could not load a plugin TODO: do something to STDOUT (?)") } // This should not pass a function func Main(f func()) { - if (Config.Debug.Debug) { - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") - } + log(debugGui, "Starting gui.Main() (using gtk via andlabs/ui)") + + InitPlugins([]string{"andlabs", "gocui"}) + for _, aplug := range allPlugins { - log.Println("gui.Node.NewButton() toolkit plugin =", aplug.name) + log(debugGui, "gui.Node.NewButton() toolkit plugin =", aplug.name) if (aplug.MainOk) { - log.Println("gui.Node.Main() Already Ran Main()", aplug.name) + log(debugGui, "gui.Node.Main() Already Ran Main()", aplug.name) continue } if (aplug.Main == nil) { - log.Println("gui.Node.Main() Main == nil", aplug.name) + log(debugGui, "gui.Node.Main() Main == nil", aplug.name) continue } aplug.MainOk = true @@ -113,10 +104,10 @@ func Main(f func()) { // Linux, MacOS and Windows work (they all work differently. suprise. surprise.) // For example: gui.Queue(NewWindow()) func Queue(f func()) { - log.Println("Sending function to gui.Main() (using gtk via andlabs/ui)") + log(debugGui, "Sending function to gui.Main() (using gtk via andlabs/ui)") // toolkit.Queue(f) for _, aplug := range allPlugins { - log.Println("gui.Node.NewButton() toolkit plugin =", aplug.name) + log(debugGui, "gui.Node.NewButton() toolkit plugin =", aplug.name) if (aplug.Queue == nil) { continue } @@ -126,24 +117,20 @@ func Queue(f func()) { // The window is destroyed but the application does not quit func StandardClose(n *Node) { - if (Config.Debug.Debug) { - log.Println("wit/gui Standard Window Close. name =", n.Name) - } + log(debugGui, "wit/gui Standard Window Close. name =", n.Name) + log(debugGui, "wit/gui Standard Window Close. n.custom exit =", n.custom) } // The window is destroyed but the application does not quit func StandardExit(n *Node) { - if (Config.Debug.Debug) { - log.Println("wit/gui Standard Window Exit. running os.Exit()") - } - - log.Println("gui.Node.StandardExit() attempt to exit each toolkit plugin") + log(debugGui, "wit/gui Standard Window Exit. running os.Exit()") + log(debugGui, "gui.Node.StandardExit() attempt to exit each toolkit plugin") for i, aplug := range allPlugins { - log.Println("gui.Node.NewButton()", i, aplug) + log(debugGui, "gui.Node.NewButton()", i, aplug) if (aplug.Quit != nil) { aplug.Quit() } } - os.Exit(0) + exit("StandardExit") } diff --git a/node.go b/node.go index c4641f5..f143771 100644 --- a/node.go +++ b/node.go @@ -5,10 +5,11 @@ package gui /* generic function to create a new node on the binary tree */ -func (n *Node) New(title string) *Node { +func (n *Node) New(title string, t string) *Node { var newN *Node newN = addNode(title, n.Width, n.Height) + newN.Widget.Type = t n.Append(newN) newN.parent = n @@ -19,7 +20,7 @@ func (n *Node) New(title string) *Node { raw create function for a new node struct */ func addNode(title string, width int, height int) *Node { - var n Node + n := new(Node) n.Name = title n.Width = width @@ -36,5 +37,5 @@ func addNode(title string, width int, height int) *Node { n.id = Config.counter Config.counter += 1 - return &n + return n } diff --git a/plugin.go b/plugin.go index e13f751..a4e007a 100644 --- a/plugin.go +++ b/plugin.go @@ -6,7 +6,6 @@ package gui // It's a pleasure to be here with all of you import ( - "log" "os" "plugin" @@ -42,6 +41,10 @@ type aplug struct { NewDropdown func(*toolkit.Widget, *toolkit.Widget) AddDropdownName func(*toolkit.Widget, string) + + SetDebugToolkit func(bool) + SetDebugChange func(bool) + ShowDebug func() } var allPlugins []*aplug @@ -50,13 +53,13 @@ var allPlugins []*aplug func LoadToolkit(name string) bool { var newPlug aplug - log.Println("gui.LoadToolkit() START") + log(debugGui, "gui.LoadToolkit() START") newPlug.LoadOk = false for _, aplug := range allPlugins { - log.Println("gui.LoadToolkit() already loaded toolkit plugin =", aplug.name) + log(debugGui, "gui.LoadToolkit() already loaded toolkit plugin =", aplug.name) if (aplug.name == name) { - log.Println("gui.LoadToolkit() SKIPPING") + log(debugGui, "gui.LoadToolkit() SKIPPING") return true } } @@ -92,13 +95,20 @@ func LoadToolkit(name string) bool { newPlug.NewDropdown = loadFunc2(&newPlug, "NewDropdown") newPlug.AddDropdownName = loadFuncS(&newPlug, "AddDropdownName") + newPlug.SetDebugToolkit = loadFuncB(&newPlug, "SetDebugToolkit") + newPlug.SetDebugChange = loadFuncB(&newPlug, "SetDebugChange") + newPlug.ShowDebug = loadFuncE(&newPlug, "ShowDebug") + allPlugins = append(allPlugins, &newPlug) - log.Println("gui.LoadToolkit() END", newPlug.name, filename) + log(debugGui, "gui.LoadToolkit() END", newPlug.name, filename) + newPlug.Init() newPlug.LoadOk = true return true } +// 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 @@ -106,13 +116,13 @@ func loadFuncE(p *aplug, funcName string) func() { test, err = p.plug.Lookup(funcName) if err != nil { - log.Println("DID NOT FIND: name =", test, "err =", err) + log(debugGui, "DID NOT FIND: name =", test, "err =", err) return nil } newfunc, ok = test.(func()) if !ok { - log.Println("function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) + log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) return nil } return newfunc @@ -125,13 +135,13 @@ func loadFunc1(p *aplug, funcName string) func(*toolkit.Widget) { test, err = p.plug.Lookup(funcName) if err != nil { - log.Println("DID NOT FIND: name =", test, "err =", err) + log(debugGui, "DID NOT FIND: name =", test, "err =", err) return nil } newfunc, ok = test.(func(*toolkit.Widget)) if !ok { - log.Println("function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) + log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) return nil } return newfunc @@ -144,13 +154,32 @@ func loadFuncS(p *aplug, funcName string) func(*toolkit.Widget, string) { test, err = p.plug.Lookup(funcName) if err != nil { - log.Println("DID NOT FIND: name =", test, "err =", err) + log(debugGui, "DID NOT FIND: name =", test, "err =", err) return nil } newfunc, ok = test.(func(*toolkit.Widget, string)) if !ok { - log.Println("function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) + log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) + return nil + } + return newfunc +} + +func loadFuncB(p *aplug, funcName string) func(bool) { + var newfunc func(bool) + 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(bool)) + if !ok { + log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) return nil } return newfunc @@ -163,13 +192,13 @@ func loadFunc2(p *aplug, funcName string) func(*toolkit.Widget, *toolkit.Widget) test, err = p.plug.Lookup(funcName) if err != nil { - log.Println("DID NOT FIND: name =", test, "err =", err) + log(debugGui, "DID NOT FIND: name =", test, "err =", err) return nil } newfunc, ok = test.(func(*toolkit.Widget, *toolkit.Widget)) if !ok { - log.Println("function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) + log(debugGui, "function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) return nil } return newfunc @@ -185,41 +214,48 @@ func loadFuncF(p *aplug, funcName string) func(func ()) { test, err = p.plug.Lookup(funcName) if err != nil { - log.Println("DID NOT FIND: name =", test, "err =", err) + log(debugGui, "DID NOT FIND: name =", test, "err =", err) return nil } newfunc, ok = test.(func(func ())) if !ok { - log.Println("function name =", funcName, "names didn't map correctly. Fix the plugin name =", p.name) + 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: + ./toolkit/ + ~/go/src/go.wit.org/gui/toolkit/ + /usr/lib/go-gui/ +*/ func loadPlugin(p *aplug, name string) { var filename string - // attempt to write out the file from the internal resource - internalName := "toolkit/" + name - soFile, err := res.ReadFile(internalName) - if (err != nil) { - log.Println(err) - } else { - err = os.WriteFile("/tmp/wit/" + name, soFile, 0644) - if (err != nil) { - log.Println(err) - } + homeDir, err := os.UserHomeDir() + if err != nil { + exit(err) } - filename = "/tmp/wit/" + name + // attempt to write out the file from the internal resource + filename = "toolkit/" + name p.plug = loadfile(filename) if (p.plug != nil) { p.filename = filename return } - filename = "/usr/share/wit/gui/" + name + filename = homeDir + "/go/src/git.wit.org/wit/gui/toolkit/" + name + p.plug = loadfile(filename) + if (p.plug != nil) { + p.filename = filename + return + } + + filename = "/usr/lib/go-gui/" + name p.plug = loadfile(filename) if (p.plug != nil) { p.filename = filename @@ -232,10 +268,10 @@ func loadPlugin(p *aplug, name string) { // 1. open the shared object file to load the symbols func loadfile(filename string) *plugin.Plugin { plug, err := plugin.Open(filename) - log.Println("plug =", plug) if err != nil { - log.Println(err) + log(debugGui, "plugin FAILED =", filename, err) return nil } + log(debugGui, "plugin WORKED =", filename) return plug } diff --git a/slider.go b/slider.go index abc1357..35867a3 100644 --- a/slider.go +++ b/slider.go @@ -1,21 +1,18 @@ package gui -import "log" - func (n *Node) NewSlider(name string, x int, y int) *Node { - newNode := n.New(name) - newNode.Widget.Name = name + newNode := n.New(name, "Slider") newNode.Widget.X = x newNode.Widget.Y = y newNode.Widget.Custom = func() { - log.Println("even newer clicker() name in NewSlider", newNode.Widget) + log(debugGui, "even newer clicker() name in NewSlider", newNode.Widget) } for _, aplug := range allPlugins { - log.Println("gui.NewSlider() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewSlider() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewSlider == nil) { - log.Println("\tgui.NewSlider() aplug.NewSlider = nil", aplug.name) + log(debugGui, "\tgui.NewSlider() aplug.NewSlider = nil", aplug.name) continue } aplug.NewSlider(&n.Widget, &newNode.Widget) diff --git a/spinner.go b/spinner.go index 565ee56..c554701 100644 --- a/spinner.go +++ b/spinner.go @@ -1,21 +1,18 @@ package gui -import "log" - func (n *Node) NewSpinner(name string, x int, y int) *Node { - newNode := n.New(name) - newNode.Widget.Name = name + newNode := n.New(name, "Spinner") newNode.Widget.X = x newNode.Widget.Y = y newNode.Widget.Custom = func() { - log.Println("even newer clicker() name in NewSpinner", newNode.Widget) + log(debugGui, "even newer clicker() name in NewSpinner", newNode.Widget) } for _, aplug := range allPlugins { - log.Println("gui.NewSpinner() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewSpinner() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewSpinner == nil) { - log.Println("\tgui.NewSpinner() aplug.NewSpinner = nil", aplug.name) + log(debugGui, "\tgui.NewSpinner() aplug.NewSpinner = nil", aplug.name) continue } aplug.NewSpinner(&n.Widget, &newNode.Widget) diff --git a/structs.go b/structs.go index 2b37ee0..271bc0b 100644 --- a/structs.go +++ b/structs.go @@ -1,8 +1,6 @@ package gui import ( - "log" - "reflect" "git.wit.org/wit/gui/toolkit" ) @@ -10,56 +8,23 @@ import ( // All GUI Data Structures and functions that are external // within the toolkit/ abstraction layer // -// More than one Window is not supported in a cross platform -// sense & may never be. On many toolkits you have to have 'tabs' -// Native Windows and MacOS toolkits work with tabs +// More than one Window does not exist in every GUI situtaion and +// can never be. On many toolkits you have to have 'tabs', like +// Native Windows and MacOS toolkits // -// If that is the case, this code should abstract the concept of -// windows and make everything 'tabs' +// If that is the case, this code abstracts the concept of +// windows and makes each window a 'tabs' in a single window. +// +// Reminder from Goals: This is for simple GUI's. +// For example, a "Mouse Control Panel" not the GIMP or blender. // var Config GuiConfig -func GetDebug () bool { - return Config.Debug.Debug -} - -func SetDebug (s bool) { - Config.Debug.Debug = s - // also set these - Config.Debug.Dump = s - Config.Debug.Node = s -} - -func GetDebugToolkit () bool { - return Config.Debug.Toolkit -} - -func SetDebugToolkit (s bool) { - Config.Debug.Toolkit = s -} - -func ShowDebugValues() { - log.Println("\t wit/gui Debug =", Config.Debug.Debug) - log.Println("\t wit/gui DebugDump =", Config.Debug.Dump) - log.Println("\t wit/gui DebugNode =", Config.Debug.Node) - log.Println("\t wit/gui DebugTabs =", Config.Debug.Tabs) - log.Println("\t wit/gui DebugPlugin =", Config.Debug.Plugin) - log.Println("\t wit/gui DebugChange =", Config.Debug.Change) - log.Println("\t wit/gui DebugToolkit =", Config.Debug.Toolkit) -} - -// This struct can be used with go-arg -type GuiDebug struct { - // These are global debugging settings - // TODO: move to a standard logging system - Debug bool - Dump bool - Node bool - Tabs bool - Plugin bool - Change bool `help:"debug mouse clicks and keyboard input"` - Toolkit bool `help:"debug toolkit"` +// This struct can be used with the go-arg package +type GuiArgs struct { + Toolkit []string `arg:"--toolkit" help:"The order to attempt loading plugins [gocui,andlabs,gtk,qt]"` + GuiDebug bool `arg:"--gui-debug" help:"debug the GUI"` } type GuiConfig struct { @@ -72,33 +37,32 @@ type GuiConfig struct { Height int Exit func(*Node) - Debug GuiDebug - // hacks depth int counter int // used to make unique ID's prefix string } -// The Node is simply the name and the size of whatever GUI element exists +// 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 type Node struct { id int + Widget toolkit.Widget + // deprecate these and use toolkit.Widget Name string Width int Height int - Widget toolkit.Widget - // this function is run when there are mouse or keyboard events OnChanged func(*Node) parent *Node - // TODO: make children a double linked list since some toolkits require order (?) children []*Node - // things that may not really be needed (?) + // is keeping + // deprecate these things if they don't really need to exist custom func() checked bool text string @@ -112,115 +76,12 @@ func (n *Node) Window() *Node { return n.parent } -func (n *Node) Dump() { - if ! Config.Debug.Dump { - return - } - IndentPrintln("NODE DUMP START") - IndentPrintln("id = ", n.id) - IndentPrintln("Name = ", n.Name) - IndentPrintln("Width = ", n.Width) - IndentPrintln("Height = ", n.Height) - - if (n.parent == nil) { - IndentPrintln("parent = nil") - } else { - IndentPrintln("parent.id =", n.parent.id) - } - if (n.children != nil) { - IndentPrintln("children = ", n.children) - } - if (n.custom != nil) { - IndentPrintln("custom = ", n.custom) - } - IndentPrintln("checked = ", n.checked) - if (n.OnChanged != nil) { - IndentPrintln("OnChanged = ", n.OnChanged) - } - IndentPrintln("text = ", reflect.ValueOf(n.text).Kind(), n.text) - IndentPrintln("NODE DUMP END") -} - func (n *Node) Append(child *Node) { n.children = append(n.children, child) - if (Config.Debug.Debug) { - log.Println("child node:") + if (debugGui) { + log(debugNode, "child node:") child.Dump() - log.Println("parent node:") + log(debugNode, "parent node:") n.Dump() } - // time.Sleep(3 * time.Second) -} - -var listChildrenParent *Node -var listChildrenDepth int = 0 -var defaultPadding = " " - -func IndentPrintln(a ...interface{}) { - indentPrintln(listChildrenDepth, defaultPadding, a) -} - -func indentPrintln(depth int, format string, a ...interface{}) { - var tabs string - for i := 0; i < depth; i++ { - tabs = tabs + format - } - - // newFormat := tabs + strconv.Itoa(depth) + " " + format - newFormat := tabs + format - log.Println(newFormat, a) -} - -func (n *Node) ListChildren(dump bool) { - indentPrintln(listChildrenDepth, defaultPadding, n.id, n.Width, n.Height, n.Name) - - if (dump == true) { - n.Dump() - } - if len(n.children) == 0 { - if (n.parent == nil) { - } else { - if (Config.Debug.Node) { - log.Println("\t\t\tparent =",n.parent.id) - } - if (listChildrenParent != nil) { - if (Config.Debug.Node) { - log.Println("\t\t\tlistChildrenParent =",listChildrenParent.id) - } - if (listChildrenParent.id != n.parent.id) { - log.Fatalln("parent.child does not match child.parent") - } - } - } - if (Config.Debug.Node) { - log.Println("\t\t", n.id, "has no children") - } - return - } - for _, child := range n.children { - // log.Println("\t\t", child.id, child.Width, child.Height, child.Name) - if (child.parent != nil) { - if (Config.Debug.Node) { - log.Println("\t\t\tparent =",child.parent.id) - } - } else { - log.Println("\t\t\tno parent") - panic("no parent") - } - if (dump == true) { - child.Dump() - } - if (Config.Debug.Node) { - if (child.children == nil) { - log.Println("\t\t", child.id, "has no children") - } else { - log.Println("\t\t\tHas children:", child.children) - } - } - listChildrenParent = n - listChildrenDepth += 1 - child.ListChildren(dump) - listChildrenDepth -= 1 - } - return } diff --git a/tab.go b/tab.go index 083e42f..6e2e47e 100644 --- a/tab.go +++ b/tab.go @@ -1,19 +1,18 @@ package gui import ( - "log" ) // This function should make a new node with the parent and // the 'tab' as a child func (n *Node) NewTab(text string) *Node { - newNode := n.New(text) + newNode := n.New(text, "Tab") for _, aplug := range allPlugins { - log.Println("gui.NewTab() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewTab() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewTab == nil) { - log.Println("\tgui.NewTab() aplug.NewTab = nil", aplug.name) + log(debugGui, "\tgui.NewTab() aplug.NewTab = nil", aplug.name) continue } aplug.NewTab(&n.Widget, &newNode.Widget) diff --git a/textbox.go b/textbox.go index 639631d..376b75d 100644 --- a/textbox.go +++ b/textbox.go @@ -1,18 +1,16 @@ package gui -import "log" - func (n *Node) NewTextbox(name string) *Node { - newNode := n.New(name) + newNode := n.New(name, "Textbox") newNode.Widget.Custom = func() { - log.Println("even newer clicker() name in NewTextBox", newNode.Widget) + log(debugGui, "wit/gui clicker()NewTextBox BUT IS EMPTY. FIXME", newNode.Widget) } for _, aplug := range allPlugins { - log.Println("gui.NewTextbox() aplug =", aplug.name, "name =", newNode.Widget.Name) + log(debugGui, "gui.NewTextbox() aplug =", aplug.name, "name =", newNode.Widget.Name) if (aplug.NewTextbox == nil) { - log.Println("\tgui.NewTextbox() aplug.NewTextbox = nil", aplug.name) + log(debugGui, "\tgui.NewTextbox() aplug.NewTextbox = nil", aplug.name) continue } aplug.NewTextbox(&n.Widget, &newNode.Widget) diff --git a/toolkit/andlabs/box.go b/toolkit/andlabs/box.go index bb9945e..463b89a 100644 --- a/toolkit/andlabs/box.go +++ b/toolkit/andlabs/box.go @@ -1,7 +1,5 @@ package main -import "log" - import "github.com/andlabs/ui" import _ "github.com/andlabs/ui/winmanifest" @@ -12,14 +10,10 @@ func (t *andlabsT) GetBox() *ui.Box { // create a new box func (t *andlabsT) NewBox() *andlabsT { - if (DebugToolkit) { - log.Println("gui.Toolbox.NewBox() START create default") - } + log(debugToolkit, "gui.Toolbox.NewBox() START create default") t.Dump() if (t.uiGroup != nil) { - if (DebugToolkit) { - log.Println("\tgui.Toolbox.NewBox() is a Group") - } + log(debugToolkit, "\tgui.Toolbox.NewBox() is a Group") var newTK andlabsT vbox := ui.NewVerticalBox() @@ -30,9 +24,7 @@ func (t *andlabsT) NewBox() *andlabsT { return &newTK } if (t.uiBox != nil) { - if (DebugToolkit) { - log.Println("\tgui.Toolbox.NewBox() is a Box") - } + log(debugToolkit, "\tgui.Toolbox.NewBox() is a Box") var newTK andlabsT vbox := ui.NewVerticalBox() @@ -44,9 +36,7 @@ func (t *andlabsT) NewBox() *andlabsT { return &newTK } if (t.uiWindow != nil) { - if (DebugToolkit) { - log.Println("\tgui.Toolbox.NewBox() is a Window") - } + log(debugToolkit, "\tgui.Toolbox.NewBox() is a Window") var newT andlabsT vbox := ui.NewVerticalBox() @@ -58,9 +48,7 @@ func (t *andlabsT) NewBox() *andlabsT { // panic("WTF") return &newT } - if (DebugToolkit) { - log.Println("\tgui.Toolbox.NewBox() FAILED. Couldn't figure out where to make a box") - } + log(debugToolkit, "\tgui.Toolbox.NewBox() FAILED. Couldn't figure out where to make a box") t.Dump() return nil } diff --git a/toolkit/andlabs/button.go b/toolkit/andlabs/button.go index bd80683..9933e1f 100644 --- a/toolkit/andlabs/button.go +++ b/toolkit/andlabs/button.go @@ -1,21 +1,20 @@ package main -import "log" -// import "os" +import ( + "github.com/andlabs/ui" + _ "github.com/andlabs/ui/winmanifest" + "git.wit.org/wit/gui/toolkit" +) -import "github.com/andlabs/ui" -import _ "github.com/andlabs/ui/winmanifest" - -import "git.wit.org/wit/gui/toolkit" func NewButton(parentW *toolkit.Widget, w *toolkit.Widget) { var t, newt *andlabsT var b *ui.Button - log.Println("gui.andlabs.NewButton()", w.Name) + log(debugToolkit, "gui.andlabs.NewButton()", w.Name) t = mapToolkits[parentW] if (t == nil) { - log.Println("go.andlabs.NewButton() toolkit struct == nil. name=", parentW.Name, w.Name) + log(debugToolkit, "go.andlabs.NewButton() toolkit struct == nil. name=", parentW.Name, w.Name) return } @@ -28,38 +27,29 @@ func NewButton(parentW *toolkit.Widget, w *toolkit.Widget) { newt.uiButton = b b.OnClicked(func(*ui.Button) { - if (DebugToolkit) { - log.Println("TODO: IN TOOLKIT GOROUTINE. SHOULD LEAVE HERE VIA channels. button name =", w.Name) - log.Println("FOUND WIDGET!", w) - } - if (w.Custom != nil) { - w.Custom() + log(debugChange, "TODO: SHOULD LEAVE Button click HERE VIA channels. button name =", w.Name) + log(debugChange, "FOUND WIDGET =", w) + if (w.Custom == nil) { + log(debugChange, "WIDGET DOES NOT have Custom()") + log(debugChange, "TODO: NOTHING TO DO button name =", w.Name) return } - if (w.Event != nil) { - w.Event(w) - return - } - t.Dump() - newt.Dump() - if (DebugToolkit) { - log.Println("TODO: LEFT TOOLKIT GOROUTINE WITH NOTHING TO DO button name =", w.Name) - } + // t.Dump() + // newt.Dump() + log(debugChange, "Running w.Custom()") + w.Custom() }) - if (DebugToolkit) { - log.Println("gui.Toolbox.NewButton() about to append to Box parent t:", w.Name) - t.Dump() - log.Println("gui.Toolbox.NewButton() about to append to Box new t:", w.Name) - newt.Dump() - } + log(debugToolkit, "gui.Toolbox.NewButton() about to append to Box parent t:", w.Name) + log(debugToolkit, "gui.Toolbox.NewButton() about to append to Box new t:", w.Name) + if (t.uiBox != nil) { t.uiBox.Append(b, stretchy) } else if (t.uiWindow != nil) { t.uiWindow.SetChild(b) } else { - log.Println("ERROR: wit/gui andlabs couldn't place this button in a box or a window") - log.Println("ERROR: wit/gui andlabs couldn't place this button in a box or a window") + log(debugToolkit, "ERROR: wit/gui andlabs couldn't place this button in a box or a window") + log(debugToolkit, "ERROR: wit/gui andlabs couldn't place this button in a box or a window") return } diff --git a/toolkit/andlabs/checkbox.go b/toolkit/andlabs/checkbox.go index b4b1524..5466d17 100644 --- a/toolkit/andlabs/checkbox.go +++ b/toolkit/andlabs/checkbox.go @@ -1,12 +1,12 @@ package main -import "log" +import "git.wit.org/wit/gui/toolkit" import "github.com/andlabs/ui" import _ "github.com/andlabs/ui/winmanifest" -func (t andlabsT) NewCheckbox(name string) *andlabsT { - log.Println("gui.Toolkit.NewCheckbox()", name) +func (t andlabsT) NewCheckbox(name string, f func()) *andlabsT { + log(debugToolkit, "gui.Toolkit.NewCheckbox()", name) var newt andlabsT if t.broken() { @@ -17,9 +17,20 @@ func (t andlabsT) NewCheckbox(name string) *andlabsT { newt.uiCheckbox = c newt.uiBox = t.uiBox t.uiBox.Append(c, stretchy) + // newt.Custom = f c.OnToggled(func(spin *ui.Checkbox) { + // log(debugToolkit, "gui.Toolkit.NewCheckbox() clicked", name) newt.commonChange("Checkbox") + /* + if (f != nil) { + log(debugToolkit, "Run custom() here", f) + log(SPEW, f) + f() + } else { + log(debugToolkit, "No custom() function here") + } + */ }) return &newt @@ -32,3 +43,27 @@ func (t andlabsT) Checked() bool { return t.uiCheckbox.Checked() } + +func NewCheckbox(parentW *toolkit.Widget, w *toolkit.Widget) { + log(debugToolkit, "gui.andlabs.NewCheckbox()", w.Name) + + t := mapToolkits[parentW] + if (t == nil) { + listMap() + } + newt := t.NewCheckbox(w.Name, w.Custom) + newt.Custom = w.Custom + /* + if (w.Custom != nil) { + log(true, "go.andlabs.NewCheckbox() toolkit struct == nil. name=", parentW.Name, w.Name) + log(true, "Run custom() START here", w.Custom) + w.Custom() + log(true, "Run custom() END") + // exit("ran it here") + } else { + log(true, "No custom() function here") + // exit("nothing here") + } + */ + mapWidgetsToolkits(w, newt) +} diff --git a/toolkit/andlabs/common.go b/toolkit/andlabs/common.go index fc6cbe8..94e19e1 100644 --- a/toolkit/andlabs/common.go +++ b/toolkit/andlabs/common.go @@ -1,37 +1,63 @@ package main -import "log" - +// This is important. This sets the defaults for the gui. Without this, there isn't correct padding, etc func init() { - if (DebugToolkit) { - log.Println("gui/toolkit init() Setting defaultBehavior = true") - } + // Can you pass values to a plugin init() ? Otherwise, there is no way to safely print + // log(debugToolkit, "gui/toolkit init() Setting defaultBehavior = true") setDefaultBehavior(true) } func (t andlabsT) commonChange(widget string) { s := t.String() - if (DebugToolkit) { - log.Println("gui.Toolkit.ui.OnChanged() =", s) - } + log(debugChange, "commonChange() START widget =", widget) + log(debugChange, "commonChange() t.String =", s) if (t.OnChanged != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.OnChanged() trying to run toolkit.OnChanged() entered val =", s) - } - t.OnChanged(&t) + // log(debugChange, "commonChange() toolkit.OnChanged() START") + // t.OnChanged(&t) + exit("OnChanged is not implemented. TODO: FIX THIS") return } if (t.Custom != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.OnChanged() Running toolkit.Custom()") - t.Dump() - } + log(debugChange, "commonChange() START toolkit.Custom()") t.Custom() + log(debugChange, "commonChange() END toolkit.Custom()") return } - if (DebugToolkit) { - log.Println("gui.Toolkit.OnChanged() ENDED without finding any callback") + if (widget == "Checkbox") { + log(debugChange, "commonChange() END Need to read the Checkbox value") + return } + if (widget == "Dropdown") { + t.getDropdown() + if (t.tw == nil) { + log(debugChange, "commonChange() END tw.Custom == nil") + } + if (t.tw.Custom == nil) { + log(debugChange, "commonChange() END Dropdown (no custom())") + } + t.tw.Custom() + log(debugChange, "commonChange() END Dropdown") + return + } + log(debugChange, "commonChange() t.String =", s) + log(debugChange, "commonChange() ENDED without finding any callback") +} + +func (t *andlabsT) getDropdown() { + log(debugChange, "commonChange() Need to read the dropdown menu") + if (t.uiCombobox == nil) { + log(debugChange, "commonChange() END BAD NEWS. t.uiCombobox == nil") + return + } + i := t.uiCombobox.Selected() + log(debugChange, "commonChange() t.uiCombobox = ", i) + if (t.tw == nil) { + log(debugChange, "commonChange() END tw = nil") + return + } + t.tw.S = t.String() + log(debugChange, "commonChange() END tw = ", t.tw) + return } // does some sanity checks on the internal structs of the binary tree @@ -39,21 +65,19 @@ func (t andlabsT) commonChange(widget string) { func (t *andlabsT) broken() bool { if (t.uiBox == nil) { if (t.uiWindow != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.UiBox == nil. This is an empty window. Try to add a box") - } + log(debugToolkit, "gui.Toolkit.UiBox == nil. This is an empty window. Try to add a box") t.NewBox() return false } - log.Println("gui.Toolkit.UiBox == nil. I can't add a widget without a place to put it") - // log.Println("probably could just make a box here?") + log(debugToolkit, "gui.Toolkit.UiBox == nil. I can't add a widget without a place to put it") + // log(debugToolkit, "probably could just make a box here?") // corruption or something horrible? panic("wit/gui toolkit/andlabs func broken() invalid goroutine access into this toolkit?") panic("wit/gui toolkit/andlabs func broken() this probably should not cause the app to panic here (?)") return true } if (t.uiWindow == nil) { - log.Println("gui.Toolkit.UiWindow == nil. I can't add a widget without a place to put it (IGNORING FOR NOW)") + log(debugToolkit, "gui.Toolkit.UiWindow == nil. I can't add a widget without a place to put it (IGNORING FOR NOW)") forceDump(t) return false } diff --git a/toolkit/andlabs/debug.go b/toolkit/andlabs/debug.go new file mode 100644 index 0000000..9b7e160 --- /dev/null +++ b/toolkit/andlabs/debug.go @@ -0,0 +1,193 @@ +package main + +// import "git.wit.org/wit/gui/toolkit" + +import "github.com/davecgh/go-spew/spew" + +var defaultBehavior bool = true + +var bookshelf bool // do you want things arranged in the box like a bookshelf or a stack? +var canvas bool // if set to true, the windows are a raw canvas +var menubar bool // for windows +var stretchy bool // expand things like buttons to the maximum size +var padded bool // add space between things like buttons +var margin bool // add space around the frames of windows + +var debugToolkit bool +var debugChange bool +// var DebugToolkit bool + +// This is important. This sets the defaults for the gui. Without this, there isn't correct padding, etc +func setDefaultBehavior(s bool) { + defaultBehavior = s + if (defaultBehavior) { + log(debugToolkit, "Setting this toolkit to use the default behavior.") + log(debugToolkit, "This is the 'guessing' part as defined by the wit/gui 'Principles'. Refer to the docs.") + stretchy = false + padded = true + menubar = true + margin = true + canvas = false + bookshelf = true // 99% of the time, things make a vertical stack of objects + } else { + log(debugToolkit, "This toolkit is set to ignore the default behavior.") + } +} + +func SetDebugToolkit (s bool) { + debugToolkit = s + log(true, "debugToolkit =", debugToolkit) + log(true, "debugChange =", debugChange) +} + +func SetDebugChange (s bool) { + debugChange = s + log(true, "debugToolkit =", debugToolkit) + log(true, "debugChange =", debugChange) +} + +func ShowDebug () { + log(true, "debugToolkit =", debugToolkit) + log(true, "debugChange =", debugChange) +} + +func GetDebugToolkit () bool { + return debugToolkit +} + +func (t *andlabsT) String() string { + return t.GetText() +} + +func forceDump(t *andlabsT) { + tmp := debugToolkit + debugToolkit = true + t.Dump() + debugToolkit = tmp +} + +func (t *andlabsT) GetText() string { + log(debugToolkit, "gui.Toolkit.GetText() Enter debugToolkit=", debugToolkit) + if (t.uiEntry != nil) { + log(debugToolkit, "gui.Toolkit.uiEntry.Text() =", t.uiEntry.Text()) + return t.uiEntry.Text() + } + if (t.uiMultilineEntry != nil) { + log(debugToolkit, "gui.Toolkit.uiMultilineEntry.Text() =", t.uiMultilineEntry.Text()) + text := t.uiMultilineEntry.Text() + log(debugToolkit, "gui.Toolkit.uiMultilineEntry.Text() =", text) + t.text = text + return text + } + if (t.uiCombobox != nil) { + log(debugToolkit, "gui.Toolkit.uiCombobox() =", t.text) + return t.text + } + return "" +} + +func (t *andlabsT) SetText(s string) bool { + log(debugToolkit, "gui.Toolkit.Text() SetText() Enter") + if (t.uiEntry != nil) { + log(debugToolkit, "gui.Toolkit.Value() =", t.uiEntry.Text) + t.uiEntry.SetText(s) + return true + } + if (t.uiMultilineEntry != nil) { + log(debugToolkit, "gui.Toolkit.Value() =", t.uiMultilineEntry.Text) + t.uiMultilineEntry.SetText(s) + return true + } + return false +} + +func sanity(t *andlabsT) bool { + if (debugToolkit) { + log(debugToolkit, "gui.Toolkit.Value() Enter") + scs := spew.ConfigState{MaxDepth: 1} + scs.Dump(t) + } + if (t.uiEntry == nil) { + log(debugToolkit, "gui.Toolkit.Value() =", t.uiEntry.Text) + return false + } + return true +} + +func (t *andlabsT) SetValue(i int) bool { + log(debugToolkit, "gui.Toolkit.SetValue() START") + if (sanity(t)) { + return false + } + t.Dump() + // panic("got to toolkit.SetValue") + return true +} + +func (t *andlabsT) Value() int { + if (debugToolkit) { + log(debugToolkit, "gui.Toolkit.Value() Enter") + scs := spew.ConfigState{MaxDepth: 1} + scs.Dump(t) + } + if (t == nil) { + log(debugToolkit, "gui.Toolkit.Value() can not get value t == nil") + return 0 + } + if (t.uiSlider != nil) { + log(debugToolkit, "gui.Toolkit.Value() =", t.uiSlider.Value) + return t.uiSlider.Value() + } + if (t.uiSpinbox != nil) { + log(debugToolkit, "gui.Toolkit.Value() =", t.uiSpinbox.Value) + return t.uiSpinbox.Value() + } + log(debugToolkit, "gui.Toolkit.Value() Could not find a ui element to get a value from") + return 0 +} + +func (t *andlabsT) Dump() { + if ! debugToolkit { + return + } + log(debugToolkit, "gui.Toolkit.Dump() Name = ", t.Name, t.Width, t.Height) + if (t.uiBox != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiBox =", t.uiBox) + } + if (t.uiButton != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiButton =", t.uiButton) + } + if (t.uiCombobox != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiCombobox =", t.uiCombobox) + } + if (t.uiWindow != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiWindow =", t.uiWindow) + } + if (t.uiTab != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiTab =", t.uiTab) + } + if (t.uiGroup != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiGroup =", t.uiGroup) + } + if (t.uiEntry != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiEntry =", t.uiEntry) + } + if (t.uiMultilineEntry != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiMultilineEntry =", t.uiMultilineEntry) + } + if (t.uiSlider != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiSlider =", t.uiSlider) + } + if (t.uiCheckbox != nil) { + log(debugToolkit, "gui.Toolkit.Dump() uiCheckbox =", t.uiCheckbox) + } + if (t.OnExit != nil) { + log(debugToolkit, "gui.Toolkit.Dump() OnExit =", t.OnExit) + } + if (t.Custom != nil) { + log(debugToolkit, "gui.Toolkit.Dump() Custom =", t.Custom) + } + log(debugToolkit, "gui.Toolkit.Dump() c =", t.c) + log(debugToolkit, "gui.Toolkit.Dump() val =", t.val) + log(debugToolkit, "gui.Toolkit.Dump() text =", t.text) +} diff --git a/toolkit/andlabs/demo.go b/toolkit/andlabs/demo.go index 0781f88..1b9a2b1 100644 --- a/toolkit/andlabs/demo.go +++ b/toolkit/andlabs/demo.go @@ -1,7 +1,5 @@ package main -import "log" - import "github.com/andlabs/ui" import _ "github.com/andlabs/ui/winmanifest" @@ -22,7 +20,7 @@ func BlankWindow(w *ui.Window) *ui.Box { func (t *andlabsT) DemoNumbersPage() { var w *ui.Window - log.Println("Starting wit/gui toolkit andlabs/ui DemoNumbersPage()") + log(debugToolkit, "Starting wit/gui toolkit andlabs/ui DemoNumbersPage()") w = t.uiWindow t.uiBox = makeNumbersPage() diff --git a/toolkit/andlabs/dropdown.go b/toolkit/andlabs/dropdown.go index 1e1886a..2691a62 100644 --- a/toolkit/andlabs/dropdown.go +++ b/toolkit/andlabs/dropdown.go @@ -1,8 +1,5 @@ package main -import "log" -// import "time" - import "github.com/andlabs/ui" import _ "github.com/andlabs/ui/winmanifest" @@ -10,11 +7,10 @@ import "git.wit.org/wit/gui/toolkit" func (t *andlabsT) NewDropdown(title string) *andlabsT { // make new node here - if (DebugToolkit) { - log.Println("gui.Toolbox.NewDropdownCombobox()", title) - } var newt andlabsT + log(debugToolkit, "gui.Toolbox.NewDropdownCombobox()", title) + if t.broken() { return nil } @@ -31,7 +27,7 @@ func (t *andlabsT) NewDropdown(title string) *andlabsT { s.OnSelected(func(spin *ui.Combobox) { i := spin.Selected() if (newt.val == nil) { - log.Println("make map didn't work") + log(debugToolkit, "make map didn't work") newt.text = "error" } newt.text = newt.val[i] @@ -44,7 +40,7 @@ func (t *andlabsT) NewDropdown(title string) *andlabsT { func (t *andlabsT) AddDropdownName(title string) { t.uiCombobox.Append(title) if (t.val == nil) { - log.Println("make map didn't work") + log(debugToolkit, "make map didn't work") return } t.val[t.c] = title @@ -56,34 +52,36 @@ func (t andlabsT) SetDropdown(i int) { } func NewDropdown(parentW *toolkit.Widget, w *toolkit.Widget) { - log.Println("gui.andlabs.NewDropdown()", w.Name) + log(debugToolkit, "gui.andlabs.NewDropdown()", w.Name) t := mapToolkits[parentW] if (t == nil) { - log.Println("go.andlabs.NewDropdown() toolkit struct == nil. name=", parentW.Name, w.Name) + log(debugToolkit, "go.andlabs.NewDropdown() toolkit struct == nil. name=", parentW.Name, w.Name) listMap() } newt := t.NewDropdown(w.Name) + newt.Custom = w.Custom + newt.tw = w mapWidgetsToolkits(w, newt) } func AddDropdownName(w *toolkit.Widget, s string) { - log.Println("gui.andlabs.AddDropdownName()", w.Name, "add:", s) + log(debugToolkit, "gui.andlabs.AddDropdownName()", w.Name, "add:", s) t := mapToolkits[w] if (t == nil) { - log.Println("go.andlabs.AddDropdownName() toolkit struct == nil. name=", w.Name, s) + log(debugToolkit, "go.andlabs.AddDropdownName() toolkit struct == nil. name=", w.Name, s) listMap() } t.AddDropdownName(s) } func SetDropdown(w *toolkit.Widget, i int) { - log.Println("gui.andlabs.SetDropdown()", i) + log(debugToolkit, "gui.andlabs.SetDropdown()", i) t := mapToolkits[w] if (t == nil) { - log.Println("go.andlabs.SetDropdown() toolkit struct == nil. name=", w.Name, i) + log(debugToolkit, "go.andlabs.SetDropdown() toolkit struct == nil. name=", w.Name, i) listMap() } t.SetDropdown(i) diff --git a/toolkit/andlabs/group.go b/toolkit/andlabs/group.go index e93247a..1762b7f 100644 --- a/toolkit/andlabs/group.go +++ b/toolkit/andlabs/group.go @@ -1,8 +1,6 @@ package main import ( - "log" - "git.wit.org/wit/gui/toolkit" "github.com/andlabs/ui" @@ -10,11 +8,11 @@ import ( ) func NewGroup(parentW *toolkit.Widget, w *toolkit.Widget) { - log.Println("gui.andlabs.NewGroup()", w.Name) + log(debugToolkit, "gui.andlabs.NewGroup()", w.Name) t := mapToolkits[parentW] if (t == nil) { - log.Println("go.andlabs.NewGroup() toolkit struct == nil. name=", parentW.Name, w.Name) + log(debugToolkit, "go.andlabs.NewGroup() toolkit struct == nil. name=", parentW.Name, w.Name) listMap() } newt := t.NewGroup(w.Name) @@ -25,9 +23,8 @@ func NewGroup(parentW *toolkit.Widget, w *toolkit.Widget) { func (t andlabsT) NewGroup(title string) *andlabsT { var newt andlabsT - if (DebugToolkit) { - log.Println("gui.Toolbox.NewGroup() create", title) - } + log(debugToolkit, "gui.Toolbox.NewGroup() create", title) + g := ui.NewGroup(title) g.SetMargined(margin) @@ -36,8 +33,9 @@ func (t andlabsT) NewGroup(title string) *andlabsT { } else if (t.uiWindow != nil) { t.uiWindow.SetChild(g) } else { - log.Println("gui.ToolboxNode.NewGroup() node.UiBox == nil. I can't add a range UI element without a place to put it") - log.Fatalln("probably could just make a box here?") + log(debugToolkit, "gui.ToolboxNode.NewGroup() node.UiBox == nil. I can't add a range UI element without a place to put it") + log(debugToolkit, "probably could just make a box here?") + exit("internal wit/gui error") } hbox := ui.NewVerticalBox() diff --git a/toolkit/andlabs/label.go b/toolkit/andlabs/label.go index c5a6896..e990b42 100644 --- a/toolkit/andlabs/label.go +++ b/toolkit/andlabs/label.go @@ -1,42 +1,72 @@ package main -import "log" +import ( + "github.com/andlabs/ui" + _ "github.com/andlabs/ui/winmanifest" -import "github.com/andlabs/ui" -import _ "github.com/andlabs/ui/winmanifest" + "git.wit.org/wit/gui/toolkit" +) -import "git.wit.org/wit/gui/toolkit" +var pwLabel *toolkit.Widget +var wLabel *toolkit.Widget +var tmpNewt *andlabsT func NewLabel(parentW *toolkit.Widget, w *toolkit.Widget) { - var t, newt *andlabsT - log.Println("gui.andlabs.NewButton()", w.Name) + pwLabel = parentW + wLabel = w + tmpNewt = new(andlabsT) + tmpNewt.Width = 10 + log(debugToolkit, "mapWidgets in ui.QueueMain() START newt =", tmpNewt.Width, tmpNewt) + if (tmpNewt == nil) { + log(debugToolkit, "mapWidgets WHY THE HELL IS THIS NIL?", tmpNewt.Width, tmpNewt) + } + ui.QueueMain(newLabel) - t = mapToolkits[parentW] + log(true, "sleep(.2) HACK. TODO: wrap spinlock around andlabs.ui goroutine") + // log(true, "sleep(.2) HACK. TODO: verify newLabel() is running inside andlabs/ui goroutine") // verified that worked + sleep(.2) + log(debugToolkit, "mapWidgets parentW/wLabel =", pwLabel) + log(debugToolkit, "mapWidgets new/newt =", tmpNewt) + mapWidgetsToolkits(w, tmpNewt) + + /* + t := mapToolkits[parentW] if (t == nil) { - log.Println("go.andlabs.NewButton() toolkit struct == nil. name=", parentW.Name, w.Name) + log(debugToolkit, "go.andlabs.NewDropdown() toolkit struct == nil. name=", parentW.Name, w.Name) + listMap() + } + newt := t.NewDropdown(w.Name) + mapWidgetsToolkits(w, newt) + */ +} + +func newLabel() { + var t, newt *andlabsT + log(debugToolkit, "gui.andlabs.NewButton()", wLabel.Name) + + t = mapToolkits[pwLabel] + if (t == nil) { + log(debugToolkit, "go.andlabs.NewButton() toolkit struct == nil. name=", pwLabel.Name, wLabel.Name) return } if t.broken() { return } - newt = new(andlabsT) + newt = tmpNewt - newt.uiLabel = ui.NewLabel(w.Name) + newt.uiLabel = ui.NewLabel(wLabel.Name) newt.uiBox = t.uiBox - if (DebugToolkit) { - log.Println("gui.Toolbox.NewButton() about to append to Box parent t:", w.Name) - t.Dump() - log.Println("gui.Toolbox.NewButton() about to append to Box new t:", w.Name) - newt.Dump() - } + log(debugToolkit, "gui.Toolbox.NewButton() about to append to Box parent t:", wLabel.Name) + t.Dump() + log(debugToolkit, "gui.Toolbox.NewButton() about to append to Box new t:", wLabel.Name) + newt.Dump() + if (t.uiBox != nil) { t.uiBox.Append(newt.uiLabel, false) } else { - log.Println("ERROR: wit/gui andlabs couldn't place this label in a box") + log(debugToolkit, "ERROR: wit/gui andlabs couldn't place this label in a box") return } - - mapWidgetsToolkits(w, newt) } diff --git a/toolkit/andlabs/log.go b/toolkit/andlabs/log.go new file mode 100644 index 0000000..fff5ba8 --- /dev/null +++ b/toolkit/andlabs/log.go @@ -0,0 +1,136 @@ +// +// version v1.2 +// +// I like things to be easy. +// +// this means all the log settings are in one place. it should allow +// things to be over-ridden externally to the library +// but still allow command line --args to pass debugging settings +// +// I also have a generic sleep() and exit() in here because it's simple +// +// Usage: +// +// log("something", foo, bar) +// var DEBUG bool = true +// log(DEBUG, "something else", someOtherVariable) # if DEBUG == false, return doing nothing +// log(SPEW, "something else", someOtherVariable) # this get's sent to spew.Dump(). Very useful for debugging! +// +package main + +import ( + "os" + "runtime" + "runtime/pprof" + golog "log" + "time" + "reflect" + "github.com/davecgh/go-spew/spew" + // "net" +) + +var LOGOFF bool = false // turn this off, all logging stops +var WARN bool +var INFO bool + +type spewt struct { + a bool +} + +var SPEW spewt + + +/* + sleep() # you know what this does? sleeps for 1 second. yep. dump. easy. + sleep(.1) # you know what this does? yes, it sleeps for 1/10th of a second +*/ +func sleep(a ...any) { + if (a == nil) { + time.Sleep(time.Second) + return + } + + log(true, "sleep", a[0]) + + switch a[0].(type) { + case int: + time.Sleep(time.Duration(a[0].(int)) * time.Second) + case float64: + time.Sleep(time.Duration(a[0].(float64) * 1000) * time.Millisecond) + default: + log("sleep a[0], type = ", a[0], reflect.TypeOf(a[0])) + } +} + +/* + exit() # yep. exits. I guess everything must be fine + exit(3) # I guess 3 it is then + exit("dont like apples") # ok. I'll make a note of that +*/ +func exit(a ...any) { + log(true, "exit", a) + //if (a) { + // os.Exit(a) + //} + os.Exit(0) +} + +/* + I've spent, am spending, too much time thinking about 'logging'. 'log', 'logrus', 'zap', whatever. + I'm not twitter. i don't give a fuck about how many nanoseconds it takes to log. Anyway, this + implementation is probably faster than all of those because you just set one bool to FALSE + and it all stops. + Sometimes I need to capture to stdout, sometimes stdout can't + work because it doesn't exist for the user. This whole thing is a PITA. Then it's spread + over 8 million references in every .go file. I'm tapping out and putting + it in one place. here it is. Also, this makes having debug levels really fucking easy. + You can define whatever level of logging you want from anywhere (command line) etc. + + log() # doesn't do anything + log(stuff) # sends it to whatever log you define in a single place. here is the place +*/ + +func log(a ...any) { + if (LOGOFF) { + return + } + + if (a == nil) { + return + } + var blah bool + if (reflect.TypeOf(a[0]) == reflect.TypeOf(blah)) { + // golog.Println("\t a[0] = bool") + if (a[0] == false) { + return + } + a[0] = "WIT/GUI/Toolkit" + } + + if (reflect.TypeOf(a[0]) == reflect.TypeOf(SPEW)) { + // a = a[1:] + a[0] = "WIT/GUI/Toolkit" + if (debugToolkit) { + spew.Dump(a) + } + return + } + + golog.Println(a...) +} + +func loggo() { + pprof.Lookup("goroutine").WriteTo(os.Stdout, 1) + golog.Println("runtime.NumGoroutine() = ", runtime.NumGoroutine()) +} + +func logindent(depth int, format string, a ...interface{}) { + var tabs string + for i := 0; i < depth; i++ { + tabs = tabs + format + } + + // newFormat := tabs + strconv.Itoa(depth) + " " + format + newFormat := tabs + format + log(debugToolkit, newFormat, a) +} diff --git a/toolkit/andlabs/main.go b/toolkit/andlabs/main.go index 85e6913..73aaad5 100644 --- a/toolkit/andlabs/main.go +++ b/toolkit/andlabs/main.go @@ -1,9 +1,6 @@ package main import ( - "log" -// "time" - "git.wit.org/wit/gui/toolkit" "github.com/andlabs/ui" @@ -12,16 +9,14 @@ import ( ) func Main(f func()) { - if (DebugToolkit) { - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") - } + log(debugToolkit, "Starting gui.Main() (using gtk via andlabs/ui)") ui.Main( func() { - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") - log.Println("Starting gui.Main() (using gtk via andlabs/ui)") + log(debugToolkit, "Starting gui.Main() (using gtk via andlabs/ui)") + log(debugToolkit, "Starting gui.Main() (using gtk via andlabs/ui)") + log(debugToolkit, "Starting gui.Main() (using gtk via andlabs/ui)") + log(debugToolkit, "Starting gui.Main() (using gtk via andlabs/ui)") + log(debugToolkit, "Starting gui.Main() (using gtk via andlabs/ui)") + log(debugToolkit, "Starting gui.Main() (using gtk via andlabs/ui)") // time.Sleep(1 * time.Second) // NewWindow2("helloworld2", 200, 100) f() @@ -37,21 +32,20 @@ func Main(f func()) { // For example: Queue(NewWindow()) // func Queue(f func()) { - if (DebugToolkit) { - log.Println("Sending function to ui.QueueMain() (using gtk via andlabs/ui)") - } - //ui.QueueMain(f) - f() + log(debugToolkit, "Sending function to ui.QueueMain() (using gtk via andlabs/ui)") + log("THIS MIGHT BREAK") + ui.QueueMain(f) + // f() } func Init() { - log.Println("should Init() here") + log(debugToolkit, "should Init() here") mapWidgets = make(map[*andlabsT]*toolkit.Widget) mapToolkits = make(map[*toolkit.Widget]*andlabsT) } func Quit() { - log.Println("should Quit() here") + log(debugToolkit, "should Quit() here") // myExit(nil) } diff --git a/toolkit/andlabs/plugin.go b/toolkit/andlabs/plugin.go index f78e95e..5165178 100644 --- a/toolkit/andlabs/plugin.go +++ b/toolkit/andlabs/plugin.go @@ -1,8 +1,6 @@ package main import ( - "log" - "git.wit.org/wit/gui/toolkit" ) @@ -13,15 +11,15 @@ var mapToolkits map[*toolkit.Widget]*andlabsT // This lists out the know mappings func listMap() { - log.Println("listMap() HERE") - log.Println("listMap() HERE") - log.Println("listMap() HERE mapWidgets()") + log(debugToolkit, "listMap() HERE") + log(debugToolkit, "listMap() HERE") + log(debugToolkit, "listMap() HERE mapWidgets()") for t, w := range mapWidgets { - log.Println("andlabs =", t.Name, "widget =", w.Name) + log(debugToolkit, "andlabs =", t.Name, "widget =", w.Name) } - log.Println("listMap() HERE mapToolkits()") + log(debugToolkit, "listMap() HERE mapToolkits()") for w, t := range mapToolkits { - log.Println("andlabs =", t, "widget =", w.Name) + log(debugToolkit, "andlabs =", t, "widget =", w.Name) forceDump(t) } } @@ -30,14 +28,22 @@ func mapWidgetsToolkits(w *toolkit.Widget, t *andlabsT) { if (mapToolkits[w] == nil) { mapToolkits[w] = t } else { - log.Println("WTF: mapToolkits already installed") - panic("WTF") + log(debugToolkit, "WTF: mapToolkits was sent nil. this should not happen w =", w) + log(debugToolkit, "WTF: mapToolkits was sent nil. this should not happen t =", t.Width) + log(debugToolkit, "WTF: mapToolkits map already set to ", mapToolkits[w]) + panic("WTF mapWidgetsToolkits() w == nil") } if (mapWidgets[t] == nil) { mapWidgets[t] = w } else { - log.Println("WTF: mapWidgets already installed") - panic("WTF") + log(debugToolkit, "WTF: mapWidgets already installed. w =", w) + log(debugToolkit, "WTF: mapWidgets already installed. t =", t.Width, t) + log(SPEW, &t) + log(SPEW, t) + log(SPEW, *t) + log(debugToolkit, "WTF: mapWidgets already mapped to", mapWidgets[t]) + log(SPEW, mapWidgets[t]) + panic("WTF. mapWidget andlabs toolkit already mapped to gui toolkit") } } diff --git a/toolkit/andlabs/slider.go b/toolkit/andlabs/slider.go index f9ff0f3..4857935 100644 --- a/toolkit/andlabs/slider.go +++ b/toolkit/andlabs/slider.go @@ -1,9 +1,6 @@ package main import ( - "log" - "os" - "git.wit.org/wit/gui/toolkit" "github.com/andlabs/ui" @@ -12,13 +9,13 @@ import ( func (t andlabsT) NewSlider(title string, x int, y int) *andlabsT { // make new node here - log.Println("gui.Toolkit.NewSpinbox()", x, y) + log(debugToolkit, "gui.Toolkit.NewSpinbox()", x, y) var newt andlabsT if (t.uiBox == nil) { - log.Println("gui.ToolkitNode.NewGroup() node.UiBox == nil. I can't add a range UI element without a place to put it") - log.Println("probably could just make a box here?") - os.Exit(0) + log(debugToolkit, "gui.ToolkitNode.NewGroup() node.UiBox == nil. I can't add a range UI element without a place to put it") + log(debugToolkit, "probably could just make a box here?") + exit("internal golang wit/gui/toolkit error") return nil } @@ -36,11 +33,11 @@ func (t andlabsT) NewSlider(title string, x int, y int) *andlabsT { func NewSlider(parentW *toolkit.Widget, w *toolkit.Widget) { var newt *andlabsT - log.Println("gui.andlabs.NewTab()", w.Name) + log(debugToolkit, "gui.andlabs.NewTab()", w.Name) t := mapToolkits[parentW] if (t == nil) { - log.Println("go.andlabs.NewTab() toolkit struct == nil. name=", parentW.Name, w.Name) + log(debugToolkit, "go.andlabs.NewTab() toolkit struct == nil. name=", parentW.Name, w.Name) return } newt = t.NewSlider(w.Name, w.X, w.Y) diff --git a/toolkit/andlabs/spinner.go b/toolkit/andlabs/spinner.go index 6505b48..b98fb0c 100644 --- a/toolkit/andlabs/spinner.go +++ b/toolkit/andlabs/spinner.go @@ -1,19 +1,16 @@ package main -import "log" -import "os" - import "github.com/andlabs/ui" import _ "github.com/andlabs/ui/winmanifest" func (t andlabsT) NewSpinner(title string, x int, y int) *andlabsT { // make new node here - log.Println("gui.Toolkit.NewSpinner()", x, y) + log(debugToolkit, "gui.Toolkit.NewSpinner()", x, y) var newt andlabsT if (t.uiBox == nil) { - log.Println("gui.ToolkitNode.NewSpinner() node.UiBox == nil. I can't add a range UI element without a place to put it") - os.Exit(0) + log(debugToolkit, "gui.ToolkitNode.NewSpinner() node.UiBox == nil. I can't add a range UI element without a place to put it") + exit("internal golang wit/gui error") return nil } diff --git a/toolkit/andlabs/structs.go b/toolkit/andlabs/structs.go index 2f3fa72..cf3afaf 100644 --- a/toolkit/andlabs/structs.go +++ b/toolkit/andlabs/structs.go @@ -1,51 +1,10 @@ package main -import "log" +import "git.wit.org/wit/gui/toolkit" import "github.com/andlabs/ui" import _ "github.com/andlabs/ui/winmanifest" -import "github.com/davecgh/go-spew/spew" - -var defaultBehavior bool = true - -var bookshelf bool // do you want things arranged in the box like a bookshelf or a stack? -var canvas bool // if set to true, the windows are a raw canvas -var menubar bool // for windows -var stretchy bool // expand things like buttons to the maximum size -var padded bool // add space between things like buttons -var margin bool // add space around the frames of windows - -var DebugToolkit bool - -func setDefaultBehavior(s bool) { - defaultBehavior = s - if (defaultBehavior) { - if (DebugToolkit) { - log.Println("Setting this toolkit to use the default behavior.") - log.Println("This is the 'guessing' part as defined by the wit/gui 'Principles'. Refer to the docs.") - } - stretchy = false - padded = true - menubar = true - margin = true - canvas = false - bookshelf = true // 99% of the time, things make a vertical stack of objects - - DebugToolkit = false - } else { - log.Println("This toolkit is set to ignore the default behavior.") - } -} - -func SetDebugToolkit (s bool) { - DebugToolkit = s -} - -func GetDebugToolkit () bool { - return DebugToolkit -} - // stores the raw toolkit internals type andlabsT struct { id string @@ -53,6 +12,7 @@ type andlabsT struct { Name string Width int Height int + tw *toolkit.Widget OnChanged func(*andlabsT) OnExit func(*andlabsT) @@ -83,167 +43,3 @@ type andlabsT struct { val map[int]string text string } - -func (t *andlabsT) String() string { - return t.GetText() -} - -func forceDump(t *andlabsT) { - tmp := DebugToolkit - DebugToolkit = true - t.Dump() - DebugToolkit = tmp -} - -func (t *andlabsT) GetText() string { - t.Dump() - if (DebugToolkit) { - log.Println("gui.Toolkit.Text() Enter") - scs := spew.ConfigState{MaxDepth: 1} - scs.Dump(t) - } - if (t.uiEntry != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() =", t.uiEntry.Text()) - } - return t.uiEntry.Text() - } - if (t.uiMultilineEntry != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() =", t.uiMultilineEntry.Text()) - } - text := t.uiMultilineEntry.Text() - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() text =", text) - } - t.text = text - return text - } - if (t.uiCombobox != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.GetText() =", t.text) - } - return t.text - } - return "" -} - -func (t *andlabsT) SetText(s string) bool { - if (DebugToolkit) { - log.Println("gui.Toolkit.Text() Enter") - scs := spew.ConfigState{MaxDepth: 1} - scs.Dump(t) - } - if (t.uiEntry != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() =", t.uiEntry.Text) - } - t.uiEntry.SetText(s) - return true - } - if (t.uiMultilineEntry != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() =", t.uiMultilineEntry.Text) - } - t.uiMultilineEntry.SetText(s) - return true - } - return false -} - -func sanity(t *andlabsT) bool { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() Enter") - scs := spew.ConfigState{MaxDepth: 1} - scs.Dump(t) - } - if (t.uiEntry == nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() =", t.uiEntry.Text) - } - return false - } - return true -} - -func (t *andlabsT) SetValue(i int) bool { - log.Println("gui.Toolkit.SetValue() START") - if (sanity(t)) { - return false - } - t.Dump() - // panic("got to toolkit.SetValue") - return true -} - -func (t *andlabsT) Value() int { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() Enter") - scs := spew.ConfigState{MaxDepth: 1} - scs.Dump(t) - } - if (t == nil) { - log.Println("gui.Toolkit.Value() can not get value t == nil") - return 0 - } - if (t.uiSlider != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() =", t.uiSlider.Value) - } - return t.uiSlider.Value() - } - if (t.uiSpinbox != nil) { - if (DebugToolkit) { - log.Println("gui.Toolkit.Value() =", t.uiSpinbox.Value) - } - return t.uiSpinbox.Value() - } - log.Println("gui.Toolkit.Value() Could not find a ui element to get a value from") - return 0 -} - -func (t *andlabsT) Dump() { - if ! DebugToolkit { - return - } - log.Println("gui.Toolkit.Dump() Name = ", t.Name, t.Width, t.Height) - if (t.uiBox != nil) { - log.Println("gui.Toolkit.Dump() uiBox =", t.uiBox) - } - if (t.uiButton != nil) { - log.Println("gui.Toolkit.Dump() uiButton =", t.uiButton) - } - if (t.uiCombobox != nil) { - log.Println("gui.Toolkit.Dump() uiCombobox =", t.uiCombobox) - } - if (t.uiWindow != nil) { - log.Println("gui.Toolkit.Dump() uiWindow =", t.uiWindow) - } - if (t.uiTab != nil) { - log.Println("gui.Toolkit.Dump() uiTab =", t.uiTab) - } - if (t.uiGroup != nil) { - log.Println("gui.Toolkit.Dump() uiGroup =", t.uiGroup) - } - if (t.uiEntry != nil) { - log.Println("gui.Toolkit.Dump() uiEntry =", t.uiEntry) - } - if (t.uiMultilineEntry != nil) { - log.Println("gui.Toolkit.Dump() uiMultilineEntry =", t.uiMultilineEntry) - } - if (t.uiSlider != nil) { - log.Println("gui.Toolkit.Dump() uiSlider =", t.uiSlider) - } - if (t.uiCheckbox != nil) { - log.Println("gui.Toolkit.Dump() uiCheckbox =", t.uiCheckbox) - } - if (t.OnExit != nil) { - log.Println("gui.Toolkit.Dump() OnExit =", t.OnExit) - } - if (t.Custom != nil) { - log.Println("gui.Toolkit.Dump() Custom =", t.Custom) - } - log.Println("gui.Toolkit.Dump() c =", t.c) - log.Println("gui.Toolkit.Dump() val =", t.val) - log.Println("gui.Toolkit.Dump() text =", t.text) -} diff --git a/toolkit/andlabs/tab.go b/toolkit/andlabs/tab.go index 0556fb9..f9085b4 100644 --- a/toolkit/andlabs/tab.go +++ b/toolkit/andlabs/tab.go @@ -1,9 +1,6 @@ package main import ( - "log" - "time" - "git.wit.org/wit/gui/toolkit" "github.com/andlabs/ui" @@ -26,32 +23,30 @@ func (t *andlabsT) newTab(name string) *andlabsT { // var w *ui.Window var newt *andlabsT - log.Println("gui.toolkit.AddTab() sleep 3") + log(debugToolkit, "gui.toolkit.AddTab()") if (t.uiWindow == nil) { - log.Println("gui.Toolkit.UiWindow == nil. I can't add a toolbar without window") + log(debugToolkit, "gui.Toolkit.UiWindow == nil. I can't add a toolbar without window") return nil } if (t.uiTab == nil) { // this means you have to make a new tab - log.Println("gui.toolkit.NewTab() GOOD. This should be the first tab:", name) + log(debugToolkit, "gui.toolkit.NewTab() GOOD. This should be the first tab:", name) newt = newTab(t.uiWindow, name) t.uiTab = newt.uiTab } else { // this means you have to append a tab - log.Println("gui.toolkit.NewTab() GOOD. This should be an additional tab:", name) + log(debugToolkit, "gui.toolkit.NewTab() GOOD. This should be an additional tab:", name) newt = t.appendTab(name) } newt.Name = name - if (DebugToolkit) { - log.Println("t:") - t.Dump() - log.Println("newt:") - newt.Dump() - } + log(debugToolkit, "t:") + t.Dump() + log(debugToolkit, "newt:") + newt.Dump() return newt } @@ -62,29 +57,23 @@ func (t *andlabsT) newTab(name string) *andlabsT { func tabSetMargined(tab *ui.Tab) { c := tab.NumPages() for i := 0; i < c; i++ { - if (DebugToolkit) { - log.Println("SetMargined", i, margin) - } + log(debugToolkit, "SetMargined", i, margin) tab.SetMargined(i, margin) } } func newTab(w *ui.Window, name string) *andlabsT { var t andlabsT - if (DebugToolkit) { - log.Println("gui.toolkit.NewTab() ADD", name) - } + log(debugToolkit, "gui.toolkit.NewTab() ADD", name) if (w == nil) { - log.Println("gui.toolkit.NewTab() node.UiWindow == nil. I can't add a tab without a window") - log.Println("gui.toolkit.NewTab() node.UiWindow == nil. I can't add a tab without a window") - log.Println("gui.toolkit.NewTab() node.UiWindow == nil. I can't add a tab without a window") - time.Sleep(1 * time.Second) + log(debugToolkit, "gui.toolkit.NewTab() node.UiWindow == nil. I can't add a tab without a window") + log(debugToolkit, "gui.toolkit.NewTab() node.UiWindow == nil. I can't add a tab without a window") + log(debugToolkit, "gui.toolkit.NewTab() node.UiWindow == nil. I can't add a tab without a window") + sleep(1) return nil } - if (DebugToolkit) { - log.Println("gui.toolkit.AddTab() START name =", name) - } + log(debugToolkit, "gui.toolkit.AddTab() START name =", name) tab := ui.NewTab() w.SetMargined(margin) @@ -102,17 +91,13 @@ func newTab(w *ui.Window, name string) *andlabsT { func (t *andlabsT) appendTab(name string) *andlabsT { var newT andlabsT - if (DebugToolkit) { - log.Println("gui.toolkit.NewTab() ADD", name) - } + log(debugToolkit, "gui.toolkit.NewTab() ADD", name) if (t.uiTab == nil) { - log.Println("gui.Toolkit.UiWindow == nil. I can't add a widget without a place to put it") + log(debugToolkit, "gui.Toolkit.UiWindow == nil. I can't add a widget without a place to put it") panic("should never have happened. wit/gui/toolkit has ui.Tab == nil") } - if (DebugToolkit) { - log.Println("gui.toolkit.AddTab() START name =", name) - } + log(debugToolkit, "gui.toolkit.AddTab() START name =", name) var hbox *ui.Box if (defaultBehavior) { @@ -135,11 +120,11 @@ func (t *andlabsT) appendTab(name string) *andlabsT { func NewTab(parentW *toolkit.Widget, w *toolkit.Widget) { var newt *andlabsT - log.Println("gui.andlabs.NewTab()", w.Name) + log(debugToolkit, "gui.andlabs.NewTab()", w.Name) t := mapToolkits[parentW] if (t == nil) { - log.Println("go.andlabs.NewTab() toolkit struct == nil. name=", parentW.Name, w.Name) + log(debugToolkit, "go.andlabs.NewTab() toolkit struct == nil. name=", parentW.Name, w.Name) return } newt = t.newTab(w.Name) diff --git a/toolkit/andlabs/textbox.go b/toolkit/andlabs/textbox.go index c7a9390..cb6075d 100644 --- a/toolkit/andlabs/textbox.go +++ b/toolkit/andlabs/textbox.go @@ -1,7 +1,5 @@ package main -import "log" - import "git.wit.org/wit/gui/toolkit" import "github.com/andlabs/ui" @@ -10,9 +8,7 @@ import _ "github.com/andlabs/ui/winmanifest" func (t andlabsT) NewTextbox(name string) *andlabsT { var newt andlabsT - if (DebugToolkit) { - log.Println("gui.Toolkit.NewTextbox()", name) - } + log(debugToolkit, "gui.Toolkit.NewTextbox()", name) if t.broken() { return nil } @@ -37,11 +33,11 @@ func (t andlabsT) NewTextbox(name string) *andlabsT { func NewTextbox(parentW *toolkit.Widget, w *toolkit.Widget) { var t, newt *andlabsT - log.Println("gui.andlabs.NewTextbox()", w.Name) + log(debugToolkit, "gui.andlabs.NewTextbox()", w.Name) t = mapToolkits[parentW] if (t == nil) { - log.Println("go.andlabs.NewTextbox() toolkit struct == nil. name=", parentW.Name, w.Name) + log(debugToolkit, "go.andlabs.NewTextbox() toolkit struct == nil. name=", parentW.Name, w.Name) return } @@ -53,16 +49,15 @@ func NewTextbox(parentW *toolkit.Widget, w *toolkit.Widget) { newt.uiLabel = ui.NewLabel(w.Name) newt.uiBox = t.uiBox - if (DebugToolkit) { - log.Println("gui.Toolbox.NewTextbox() about to append to Box parent t:", w.Name) - t.Dump() - log.Println("gui.Toolbox.NewTextbox() about to append to Box new t:", w.Name) - newt.Dump() - } + log(debugToolkit, "gui.Toolbox.NewTextbox() about to append to Box parent t:", w.Name) + t.Dump() + log(debugToolkit, "gui.Toolbox.NewTextbox() about to append to Box new t:", w.Name) + newt.Dump() + if (t.uiBox != nil) { t.uiBox.Append(newt.uiLabel, false) } else { - log.Println("ERROR: wit/gui andlabs couldn't place this Textbox in a box") + log(debugToolkit, "ERROR: wit/gui andlabs couldn't place this Textbox in a box") return } diff --git a/toolkit/andlabs/window.go b/toolkit/andlabs/window.go index b360cb8..7527ac5 100644 --- a/toolkit/andlabs/window.go +++ b/toolkit/andlabs/window.go @@ -1,8 +1,6 @@ package main import ( - "log" - "github.com/andlabs/ui" _ "github.com/andlabs/ui/winmanifest" @@ -20,12 +18,10 @@ func (t *andlabsT) ErrorWindow(msg1 string, msg2 string) { func NewWindow(w *toolkit.Widget) { var t *andlabsT - if (DebugToolkit) { - log.Println("toolkit NewWindow", w.Name, w.Width, w.Height) - } + log(debugToolkit, "toolkit NewWindow", w.Name, w.Width, w.Height) if (w == nil) { - log.Println("wit/gui plugin error. widget == nil") + log(debugToolkit, "wit/gui plugin error. widget == nil") return } t = new(andlabsT) @@ -37,21 +33,17 @@ func NewWindow(w *toolkit.Widget) { win.SetBorderless(canvas) win.SetMargined(margin) win.OnClosing(func(*ui.Window) bool { - if (DebugToolkit) { - log.Println("ui.Window().OnExit() SHOULD ATTEMPT CALLBACK here") - t.Dump() - } + log(debugToolkit, "ui.Window().OnExit() SHOULD ATTEMPT CALLBACK here") + t.Dump() if (w.Custom != nil) { w.Custom() return true } - if (w.Event != nil) { - w.Event(w) - return true - } - if (DebugToolkit) { - log.Println("andlabs.ui.Window().OnClosing() was not defined") - } + // if (w.Event != nil) { + // w.Event(w) + // return true + // } + log(debugToolkit, "andlabs.ui.Window().OnClosing() was not defined") return false }) win.Show() @@ -64,15 +56,11 @@ func NewWindow(w *toolkit.Widget) { } func (t *andlabsT) SetWindowTitle(title string) { - if (DebugToolkit) { - log.Println("toolkit NewWindow", t.Name, "title", title) - } + log(debugToolkit, "toolkit NewWindow", t.Name, "title", title) win := t.uiWindow if (win != nil) { win.SetTitle(title) } else { - if (DebugToolkit) { - log.Println("Setting the window title", title) - } + log(debugToolkit, "Setting the window title", title) } } diff --git a/toolkit/gocui/keybindings.go b/toolkit/gocui/keybindings.go index 48edf71..3443320 100644 --- a/toolkit/gocui/keybindings.go +++ b/toolkit/gocui/keybindings.go @@ -98,10 +98,10 @@ func initKeybindings(g *gocui.Gui) error { w.Custom() return nil } - if (w.Event != nil) { - w.Event(w) - return nil - } + // if (w.Event != nil) { + // w.Event(w) + // return nil + // } } return nil }); err != nil { diff --git a/toolkit/widget.go b/toolkit/widget.go index 9003546..295a598 100644 --- a/toolkit/widget.go +++ b/toolkit/widget.go @@ -1,42 +1,43 @@ package toolkit // passes information between the toolkit library (plugin) - +// // All Toolkit interactions should be done via a channel or Queue() - +// TODO: FIND THIS NOTE AND FIGURE OUT HOW TO IMPLEMENT IT +// // This is the only thing that is passed between the toolkit plugin - +// // what names should be used? This is not part of [[Graphical Widget]] // Event() seems like a good name. // Could a protobuf be used here? (Can functions be passed?) type Widget struct { - i int - s string - Name string + Type string // after lots of back and forth, a simple string + + // This GUI is intended for simple things + // We are not laying out PDF's here + // This is used for things like a slider(0,100) Width int Height int X int Y int + // latest attempt Custom func() - Event func(*Widget) *Widget - // Probably deprecate these + // This might be useful to simplify retrieving + // values from things like checkboxes & dropdown's + B bool + I int + S string + + // other things I've tried + // Event func(*Widget) *Widget // OnChanged func(*Widget) // Custom func(*Widget) // OnExit func(*Widget) } -type Blah struct { - i int - s string - - Name string - Width int - Height int -} - /* type Widget int diff --git a/watchdog.go b/watchdog.go index 29ac21a..73248dd 100644 --- a/watchdog.go +++ b/watchdog.go @@ -1,7 +1,6 @@ package gui import ( - "log" "time" ) @@ -16,7 +15,7 @@ var watchtime time.Duration = 100 // in tenths of seconds func Watchdog() { var i = 1 for { - log.Println("watchdog timer is alive. give me something to do.", i, "debug =", Config.Debug.Debug) + log(debugGui, "watchdog timer is alive. give me something to do.", i) i += 1 time.Sleep(watchtime * time.Second / 10) } diff --git a/window.go b/window.go index 9072bdd..10af3b8 100644 --- a/window.go +++ b/window.go @@ -1,7 +1,6 @@ package gui import ( - "log" ) //import toolkit "git.wit.org/wit/gui/toolkit/andlabs" @@ -17,16 +16,18 @@ func NewWindow() *Node { title := Config.Title // Windows are created off of the master node of the Binary Tree - newNode = Config.master.New(title) + newNode = Config.master.New(title, "Window") - newNode.Widget.Name = title newNode.Widget.Width = Config.Width newNode.Widget.Height = Config.Height if (Config.Exit != nil) { + log("setting a custom exit") newNode.custom = func() { Config.Exit(newNode) } + } else { + log("not setting a custom exit") } if (newNode.custom == nil) { @@ -35,12 +36,12 @@ func NewWindow() *Node { newNode.Widget.Custom = newNode.custom - log.Println("gui.Node.Window()", title) + log(debugGui, "gui.Node.Window()", title) for _, aplug := range allPlugins { - log.Println("gui.Node.NewWindow() toolkit plugin =", aplug.name) + log(debugGui, "gui.Node.NewWindow() toolkit plugin =", aplug.name) if (aplug.NewWindow == nil) { - log.Println("gui.Node.NewWindow() is nil") + log(debugGui, "gui.Node.NewWindow() is nil") continue } aplug.NewWindow(&newNode.Widget)