commit 45e0e16239111401e9999da722e182248c78d3b2
parent dce2aaec18f6b0b52b7ee5bf6603891907473823
Author: lash <dev@holbrook.no>
Date:   Sat, 29 Apr 2023 09:10:14 +0100
Add longmenu example
Diffstat:
14 files changed, 122 insertions(+), 15 deletions(-)
diff --git a/.gitignore b/.gitignore
@@ -1,2 +1,3 @@
 examples/**/*.bin
 examples/**/*.txt
+**/.state
diff --git a/Makefile b/Makefile
@@ -11,3 +11,6 @@ helloworld:
 
 validate:
 	make -C examples/validate
+
+longmenu:
+	make -C examples/longmenu
diff --git a/asm/asm.go b/asm/asm.go
@@ -297,7 +297,7 @@ var (
 		{"Comment", `(?:#)[^\n]*`},
 		{"Ident", `^[A-Z]+`},
 		{"Size", `[0-9]+`},
-		{"Sym", `[a-zA-Z_\*\.][a-zA-Z0-9_]*`},
+		{"Sym", `[a-zA-Z_\*\.\^\<\>][a-zA-Z0-9_]*`},
 		{"Whitespace", `[ \t]+`},
 		{"EOL", `[\n\r]+`},
 		{"Quote", `["']`},
diff --git a/dev/interactive/main.go b/dev/interactive/main.go
@@ -19,7 +19,7 @@ func main() {
 	flag.UintVar(&size, "s", 0, "max size of output")
 	flag.StringVar(&root, "root", "root", "entry point symbol")
 	flag.StringVar(&sessionId, "session-id", "default", "session id")
-	flag.BoolVar(&persist, "persist", true, "use state persistence")
+	flag.BoolVar(&persist, "persist", false, "use state persistence")
 	flag.Parse()
 	fmt.Fprintf(os.Stderr, "starting session at symbol '%s' using resource dir: %s\n", root, dir)
 
diff --git a/examples/longmenu/Makefile b/examples/longmenu/Makefile
@@ -0,0 +1,10 @@
+INPUTS = $(wildcard ./*.vis)
+TXTS = $(wildcard ./*.txt.orig)
+
+%.vis:
+	go run ../../dev/asm $(basename $@).vis > $(basename $@).bin
+
+all: $(INPUTS) $(TXTS)
+
+%.txt.orig:
+	cp -v $(basename $@).orig $(basename $@)
diff --git a/examples/longmenu/main.go b/examples/longmenu/main.go
@@ -0,0 +1,58 @@
+package main
+
+import (
+	"context"
+	"flag"
+	"fmt"
+	"os"
+	"path"
+
+	testdataloader "github.com/peteole/testdata-loader"
+
+	"git.defalsify.org/vise.git/engine"
+)
+var (
+	baseDir = testdataloader.GetBasePath()
+	scriptDir = path.Join(baseDir, "examples", "longmenu")
+)
+
+func main() {
+	var root string
+	var size uint
+	var sessionId string
+	var persist bool
+	flag.UintVar(&size, "s", 0, "max size of output")
+	flag.StringVar(&root, "root", "root", "entry point symbol")
+	flag.StringVar(&sessionId, "session-id", "default", "session id")
+	flag.BoolVar(&persist, "persist", false, "use state persistence")
+	flag.Parse()
+
+	dir := scriptDir
+	fmt.Fprintf(os.Stderr, "starting session at symbol '%s' using resource dir: %s\n", root, dir)
+
+	ctx := context.Background()
+	en, err := engine.NewSizedEngine(dir, uint32(size), persist, &sessionId)
+	if err != nil {
+		fmt.Fprintf(os.Stderr, "engine create error: %v", err)
+		os.Exit(1)
+	}
+	cont, err := en.Init(ctx)
+	if err != nil {
+		fmt.Fprintf(os.Stderr, "engine init exited with error: %v\n", err)
+		os.Exit(1)
+	}
+	if !cont {
+		_, err = en.WriteResult(ctx, os.Stdout)
+		if err != nil {
+			fmt.Fprintf(os.Stderr, "dead init write error: %v\n", err)
+			os.Exit(1)
+		}
+		os.Stdout.Write([]byte{0x0a})
+		os.Exit(0)
+	}
+	err = engine.Loop(ctx, en, os.Stdin, os.Stdout)
+	if err != nil {
+		fmt.Fprintf(os.Stderr, "loop exited with error: %v\n", err)
+		os.Exit(1)
+	}
+}
diff --git a/examples/longmenu/poke.vis b/examples/longmenu/poke.vis
@@ -0,0 +1 @@
+HALT
diff --git a/examples/longmenu/root b/examples/longmenu/root
@@ -0,0 +1 @@
+showing long menu
diff --git a/examples/longmenu/root.vis b/examples/longmenu/root.vis
@@ -0,0 +1,22 @@
+MOUT inky 0
+MOUT pinky 1
+MOUT blinky 2
+MOUT clyde 3
+MOUT tinkywinky 4
+MOUT dipsy 5
+MOUT lala 6
+MOUT pu 7
+MNEXT fwdmenu 11
+MPREV backmenu 1234
+MSINK
+HALT
+INCMP poke 0
+INCMP poke 1
+INCMP poke 2
+INCMP poke 3
+INCMP poke 4
+INCMP poke 5
+INCMP poke 6
+INCMP poke 7
+INCMP > 11
+INCMP < 1234
diff --git a/render/menu.go b/render/menu.go
@@ -53,6 +53,10 @@ type Menu struct {
 	keep bool
 }
 
+func(m Menu) String() string {
+	return fmt.Sprintf("pagecount: %v sink: %v next: %v prev: %v", m.pageCount, m.sink, m.canNext, m.canPrevious)
+}
+
 // NewMenu creates a new Menu with an explicit page count.
 func NewMenu() *Menu {
 	return &Menu{
@@ -219,6 +223,7 @@ func(m *Menu) applyPage(idx uint16) error {
 	if idx == 0 {
 		m.canPrevious = false
 	}
+	Logg.Debugf("applypage", "m", m, "idx", idx)
 
 	if m.canNext {
 		err := m.Put(m.browse.NextSelector, m.browse.NextTitle)
diff --git a/render/page.go b/render/page.go
@@ -326,6 +326,7 @@ func(pg *Page) prepare(ctx context.Context, sym string, values map[string]string
 			pg.extra = "\n{{._menu}}"
 			pg.sizer.sink = sink
 			noSinkValues[sink] = ""
+			Logg.DebugCtxf(ctx, "menu is sink", "items", len(sinkValues))
 		}
 	}
 
diff --git a/render/size_test.go b/render/size_test.go
@@ -333,9 +333,9 @@ func TestMenuSink(t *testing.T) {
 	ca := cache.NewCache()
 	rs := resource.NewMemResource()
 	rs.AddTemplate("foo", "bar {{.baz}}")
-	szr := NewSizer(30)
+	szr := NewSizer(45)
 
-	mn := NewMenu().WithSink()
+	mn := NewMenu().WithSink().WithBrowseConfig(DefaultBrowseConfig())
 	mn.Put("0", "inky")
 	mn.Put("1", "pinky")
 	mn.Put("22", "blinky")
@@ -356,12 +356,14 @@ func TestMenuSink(t *testing.T) {
 	}
 	expect := `bar xyzzy
 0:inky
-1:pinky`
+1:pinky
+22:blinky
+11:next`
 	if r != expect {
 		t.Fatalf("expected:\n\t%s\ngot:\n\t%s\n", expect, r)
 	}
 
-	mn = NewMenu().WithSink()
+	mn = NewMenu().WithSink().WithBrowseConfig(DefaultBrowseConfig())
 	mn.Put("0", "inky")
 	mn.Put("1", "pinky")
 	mn.Put("22", "blinky")
@@ -379,8 +381,9 @@ func TestMenuSink(t *testing.T) {
 		t.Fatal(err)
 	}
 	expect = `bar xyzzy
-22:blinky
-3:clyde`
+3:clyde
+44:tinkywinky
+22:previous`
 	if r != expect {
 		t.Fatalf("expected:\n\t%s\ngot:\n\t%s\n", expect, r)
 	}
diff --git a/testdata/testdata.go b/testdata/testdata.go
@@ -51,9 +51,9 @@ func out(sym string, b []byte, tpl string, data map[string]string) error {
 
 func root() error {
 	b := []byte{}
-	b = vm.NewLine(b, vm.MOUT, []string{"do the foo", "1"}, nil, nil)
-	b = vm.NewLine(b, vm.MOUT, []string{"go to the bar", "2"}, nil, nil)
-	b = vm.NewLine(b, vm.MOUT, []string{"language template", "3"}, nil, nil)
+	b = vm.NewLine(b, vm.MOUT, []string{"1", "do the foo"}, nil, nil)
+	b = vm.NewLine(b, vm.MOUT, []string{"2", "go to the bar"}, nil, nil)
+	b = vm.NewLine(b, vm.MOUT, []string{"3", "language template"}, nil, nil)
 	b = vm.NewLine(b, vm.HALT, nil, nil, nil)
 	b = vm.NewLine(b, vm.INCMP, []string{"foo", "1"}, nil, nil)
 	b = vm.NewLine(b, vm.INCMP, []string{"bar", "2"}, nil, nil)
@@ -66,9 +66,9 @@ func root() error {
 
 func foo() error {
 	b := []byte{}
-	b = vm.NewLine(b, vm.MOUT, []string{"to foo", "0"}, nil, nil)
-	b = vm.NewLine(b, vm.MOUT, []string{"go bar", "1"}, nil, nil)
-	b = vm.NewLine(b, vm.MOUT, []string{"see long", "2"}, nil, nil)
+	b = vm.NewLine(b, vm.MOUT, []string{"0", "to foo"}, nil, nil)
+	b = vm.NewLine(b, vm.MOUT, []string{"1", "go bar"}, nil, nil)
+	b = vm.NewLine(b, vm.MOUT, []string{"2", "see long"}, nil, nil)
 	b = vm.NewLine(b, vm.LOAD, []string{"inky"}, []byte{20}, nil)
 	b = vm.NewLine(b, vm.HALT, nil, nil, nil)
 	b = vm.NewLine(b, vm.INCMP, []string{"_", "0"}, nil, nil)
diff --git a/vm/runner.go b/vm/runner.go
@@ -406,7 +406,9 @@ func(vm *Vm) runHalt(ctx context.Context, b []byte) ([]byte, error) {
 // executes the MSIZE opcode
 func(vm *Vm) runMSink(ctx context.Context, b []byte) ([]byte, error) {
 	b, err := ParseMSink(b)
-	vm.mn = vm.mn.WithSink()
+	mcfg := vm.mn.GetBrowseConfig()
+	vm.mn = vm.mn.WithSink().WithBrowseConfig(mcfg).WithPages()
+	//vm.pg.WithMenu(vm.mn)
 	return b, err
 }