How to refresh the PassageFooter from a passage?

Hi, I’m struggling to figure out how to refresh the footer from within a passage. Basically, I’m trying to do this but in SugarCube: Refresh score in footer immediately when incremented

My goal is to be able to toggle the footer on/off just by changing a single variable as the story progresses while staying inside the same passage.

I tried using this macro but quickly realized that PassageFooter isn’t considered a UI element.

Any help would be greatly appreciated.

If it’s not an element you can toggle by default, simply make it one. Just wrap the contents of the PassageFooter passage in something like a <div> element with an ID, then you can toggle its visibility as needed.

That said, you might want to take a look at the “Bottom and Top Bars” section of my Twine/SugarCube sample code collection. With that you could just keep the score visible at the bottom.

As for updating things while staying within the same passage, jQuery makes that quite easy (jQuery is built into SugarCube). Or you can use the various SugarCube DOM macros, such as the <<replace>> macro, to update elements you’ve added to your passages.

If you still need help after that, feel free to ask. :slight_smile:

1 Like

Your advice and sample code collection have been very helpful. Thank you.

I’ve managed to accomplish what I wanted to accomplish using the following code:

<<script>>
$(document).on(':passagedisplay', function (ev) {
	document.getElementById("footer-div").style.visibility = "hidden";
});<</script>>

I’m using the script to hide/display a “Click to continue” message so that I can remind the player to advance the dialog when waiting for an input to display the next dialog box.

Like this:

<<script>>
$(document).on(':passagedisplay', function (ev) {
	document.getElementById("footer-div").style.visibility = "";
});<</script>>
<<cont append keypress>><<character1>>How are you?<</character1>><</cont>>
<<cont append keypress>><<character2>>Fan-fucking-tastic!<</character2>><</cont>>
<<script>>
$(document).on(':passagedisplay', function (ev) {
	document.getElementById("footer-div").style.visibility = "hidden";
});<</script>>

The next part of this quest is to turn the script into a widget so I can do this:

<<exposition>>
<<cont append keypress>><<character1>>How are you?<</character1>><</cont>>
<<cont append keypress>><<character2>>Fan-fucking-tastic!<</character2>><</cont>>
<</exposition>>
[[next passage]]

But that’s not something I feel comfortable asking for help with since I should first level up my front-end skills otherwise I’m going to be here all the time posting questions, haha.

I’m not sure your “Like this:” code works like you think it does, because it looks like it would just make the footer visible and then hidden again immediately, since both :passagedisplay events in your code would happen immediately when the passage was displayed. I think you might actually want something more like this:

<<cont append keypress>><<character1>>How are you?<</character1>><</cont>>
<<cont append keypress>><<character2>>Fan-fucking-tastic!<</character2>>
<<run $("#footer-div").css({ visibility: "hidden" })>><</cont>>
<<script>>
	$(document).one(':passagedisplay', function (ev) {
		$("#footer-div").css({ visibility: "visible" });
	});
<</script>>

That would start out with the score visible in that passage and then hide the score once “character2” speaks. (I also changed the code to use the jQuery version of setting the style on an element, see the .css() method for details.) I am kind of guessing at what you actually want, though. Swap the “hidden” and “visible” if you want it the other way around.

Also, and this is very important, I changed the code to use the jQuery .one() method, instead of the .on() method that you were using. The reason why is that using the .on() method on a SugarCube event like that will add that to a list of events which trigger on every passage, which will gradually slow down your game due to adding another event trigger (or two event triggers, in your code) every time the player goes to another passage with that code. The .one() method, on the other hand, is a once-and-done event trigger, so it will only affect that one passage. If you set up an event trigger for a SugarCube event in your passages, you should always use the .one() method (this doesn’t apply to non-SugarCube event triggers). If you need the code to trigger during a SugarCube event in all passages, then that code belongs in the JavaScript section or the StoryInit special passage.

Well, if you want to do something like that, instead of creating a widget, you’ll have to create a macro using the Macro API (widgets only have a “head”, while macros can have “head” and “tail” parts, with contents inbetween, like what you want). If you take a look at the “Combining Story Passages” section of my sample code collection, that includes the code for a <<chunktext>> macro, which should get you most of the way to creating what you want.

If you need help with any coding there, please feel free to ask. :slight_smile:

P.S. Did a few important edits, so if you saw this before this “P.S.” was added, then I’d recommend going back to re-read it.

1 Like

Extremely helpful! Thank you again. You’re right, my script doesn’t actually do what I would like it to do, and I didn’t realize because I was jumping between passages when testing it instead of using it the way I described. The script you provided works like a charm.

I’ll definitely take a look at the <<chunktext>> macro this weekend.