0 votes
by (420 points)

I followed this tutorial while implementing a basic combat system (adapting the Harlowe to Sugarcube) and now I'm working on fleshing it out.  The problem I'm having is that this model uses nested passages to achieve a look of discrete display windows:

Passage Combat, the parent passage:

<<include "Enemy">>
<<include "Log">>
<<include "You">>

Passage Enemy, a child passage:

<div id="enemy">$ename HP: $ehp/$mhp</div>

Passage Log, a child passage:

<div id="log">

<<if $log is "you">>

  It is your turn. 

<<elseif $log is "atk">>

You use '$atk' on the $ename, dealing $atkdmg damage. 

<<elseif $log is "enemy">>

The $ename uses '$eatkname' on you, dealing $eatk damage.


Passage You, a child passage:

<div id="you">

You: $hp/100 

<<if $turn is "you">>

  <<link "Punch"->Combat)

    <<set $ehp -= 10>>

    <<set $atk to "Punch">> 

    <<set $atkdmg to 10>> 

    <<set $turn to "enemy">> 

    <<set $log to "atk">>


  <<link "Sword"->Combat>>

    <<set $ehp -= 30>>

    <<set $atk to "Sword">>

    <<set $atkdmg to 30>>

    <<set $turn to "enemy">>

    <<set $log to "atk">>


<<elseif $turn is "enemy">>

  <<link "Continue"->Combat>>

    <<set $log to "enemy">>

    <<set $turn to "you">>

    <<set $hp -= $eatk>>



<<if $hp < 1>><<goto "CombatLose">><</if>>
<<if $ehp < 1>><<goto "CombatWin">><</if>>


 This model relies on routing the user back through the parent Combat passage and re-including the child passages to update their displayed data.  It can be very awkward to route and re-route the user through the parent Combat passage in order to update child passages' text whenever data changes -- is there a way to tell a given Passage object that it should re-render itself because underlying data has changed?

1 Answer

+1 vote
by (44.7k points)
selected by
Best answer

There's no need to have four separate passages for that.  Remove the <<div>>s and <</div>>s from the "Enemy", "Log", and "You" passages, and combine them all into one "CombatText" passage.

Then change the "Combat" passage to just this:

<div id="combattext"><<include "CombatText">></div>

Now, to update that, all you would need to do is something like this:

<<replace "#combattext">><<include "CombatText">><</replace>>

For example:

  <<link "Punch">>
    <<set $ehp -= 10>>
    <<set $atk to "Punch">>
    <<set $atkdmg to 10>>
    <<set $turn to "enemy">>
    <<set $log to "atk">>
    <<replace "#combattext">><<include "CombatText">><</replace>>

(You don't need the "->Combat" part anymore either.)

Just put that inside each of the <<link>> macros, like in the above example, and that should do what you want.

Have fun!  :-)

by (420 points)
sounds good!  Is it possible to use the Passage API or a macro to re-render content from a passage other than the current one?
by (44.7k points)

You can render content from any passage you want, just use that passage name inside of the "<<include>>" macro.  You can even put the passage name in a variable and do "<<include $variableName>>" with that variable.  Just be careful because it is case sensitive, so setting that variable to "passage 1" won't open "Passage 1", because the "P" has different capitalization.

Hope that helps!  :-)