From 075f001107e04e10a5a10095d5e8115b7b0dccd5 Mon Sep 17 00:00:00 2001 From: Nat Quayle Nelson Date: Tue, 4 Jun 2019 16:35:03 -0600 Subject: [PATCH] Divert target vars via more interp extension. Close #48 --- examples/divert-vars/main.hank | 41 +++++++++++++++++++++++++++++++++ examples/divert-vars/test1.hlog | 7 ++++++ hank/HInterface.hx | 39 +++++++++++++++++++++++++++++-- hank/Story.hx | 5 +++- 4 files changed, 89 insertions(+), 3 deletions(-) create mode 100644 examples/divert-vars/main.hank create mode 100644 examples/divert-vars/test1.hlog diff --git a/examples/divert-vars/main.hank b/examples/divert-vars/main.hank new file mode 100644 index 0000000..5588e96 --- /dev/null +++ b/examples/divert-vars/main.hank @@ -0,0 +1,41 @@ +~ var target = ->knot1; +-> start + +== start + +-> @target + += stitch1 +Text 3 +~ target = ->stitch2; +-> start += stitch2 +Text 4 +~ target = ->gather1 +-> start +- (gather1) +Woooow! +~target = ->finish.real_finish.real_tricky; +->start + +== knot1 + +Text 1 +~ target = ->knot2 +-> start + +== knot2 + +Text 2 +~ target = ->finish; +-> start + +== finish + +Seems to have worked! Time to get more complicated. +~target = ->start.stitch1 +->start + += real_finish + +- (real_tricky) That's incredible. \ No newline at end of file diff --git a/examples/divert-vars/test1.hlog b/examples/divert-vars/test1.hlog new file mode 100644 index 0000000..6647434 --- /dev/null +++ b/examples/divert-vars/test1.hlog @@ -0,0 +1,7 @@ +Text 1 +Text 2 +Seems to have worked! Time to get more complicated. +Text 3 +Text 4 +Woooow! +That's incredible. \ No newline at end of file diff --git a/hank/HInterface.hx b/hank/HInterface.hx index fbff4f5..bac6a83 100644 --- a/hank/HInterface.hx +++ b/hank/HInterface.hx @@ -10,9 +10,14 @@ import hscript.Expr; using hank.Extensions; import hank.StoryTree; +import hank.Story; class HankInterp extends Interp { var hInterface: HInterface; + var story: Story; + public function setStory(story: Story) { + this.story = story; + } public function new(hInterface: HInterface) { this.hInterface = hInterface; super(); @@ -20,7 +25,7 @@ class HankInterp extends Interp { public override function expr(e: Expr): Dynamic { switch (e) { // pointers are actually just string keys to the Interp's variables. - // TODO Divert target variables are just fully qualified strings that can be passed to divertTo() + case EUnop("&", true, e): switch (e) { case EIdent(id): @@ -35,6 +40,28 @@ class HankInterp extends Interp { default: throw 'Dereferencing complex expressions is not implemented'; } + // TODO Divert target variables are just StoryNode values + case EUnop("->", true, e): + trace(e); + var targetWithDots = ''; + var trailingDot = false; + while (true) { + switch (e) { + case EIdent(lastTarget): + targetWithDots = lastTarget + '.' + targetWithDots; + if (trailingDot) targetWithDots = targetWithDots.substr(0,targetWithDots.length-1); + var node = story.resolveNodeInScope(targetWithDots); + trace (node); + return node; + case EField(eNested, lastTarget): + targetWithDots = lastTarget + '.' + targetWithDots; + + trailingDot = true; + e = eNested; + default: throw 'Divert target variable cannot be specified in form $e'; + } + } + default: return super.expr(e); } @@ -68,11 +95,15 @@ class HInterface { var interp: HankInterp; var viewCounts: Map; - public function new(storyTree: StoryNode, viewCounts: Map) { + public function setStory(story: Story) { + interp.setStory(story); + } + public function new(storyTree: StoryNode, viewCounts: Map) { this.parser = new Parser(); parser.unops["*"] = false; parser.unops["&"] = false; + parser.unops["->"] = false; this.interp = new HankInterp(this); this.interp.variables['_isTruthy'] = isTruthy.bind(viewCounts); @@ -149,6 +180,10 @@ class HInterface { this.interp.variables[identifier] = value; } + public function getVariable(identifier: String) { + return this.interp.variables[identifier]; + } + /** Run a pre-processed block of Haxe embedded in a Hank story. **/ diff --git a/hank/Story.hx b/hank/Story.hx index 395c352..4acd4ff 100644 --- a/hank/Story.hx +++ b/hank/Story.hx @@ -87,6 +87,7 @@ class Story { var hInterface = new HInterface(storyTree, viewCounts); var story = new Story(random, new Parser(), ast, storyTree, nodeScopes, viewCounts, hInterface); + hInterface.setStory(story); hInterface.addVariable('story', story); story.runRootIncludedHaxe(script); @@ -245,6 +246,7 @@ class Story { exprIndex = gatherIndex; } + @:allow(hank.HankInterp) private function resolveNodeInScope(label: String, ?whichScope: Array): Array { if (whichScope == null) whichScope = nodeScopes; @@ -292,8 +294,9 @@ class Story { } // trace('diverting to $target'); + - var newScopes = resolveNodeInScope(target); + var newScopes = if (target.startsWith("@")) hInterface.getVariable(target.substr(1)) else resolveNodeInScope(target); var targetIdx = newScopes[0].astIndex; if (targetIdx == -1) {