+2 votes
by (180 points)

This is my first question here, so apologies if I broke a rule I may not be aware of. I also searched the database but I couldn't seem to find what I am looking for.

Here is some context to my question:

I am currently working on a Twine game in Harlowe that will, among other things, have an rpg-like character development system. Among other things, at a certain point in the game, you level up, meaning: your max health changes from 10 to 20. 

I also have an inventory system. In the inventory menu where you also can monitor your stats, you will have the possibility of increasing your health with a potion.

Is there any way in Twine (Harlowe) I can define that the variable health should not exceed a certain value (say: 10)? Imagine every portion of potion increases your health by 5 points, and your health is at 8 – how can I define that when you take the potion it should only increase your variable health to 10 (and not to 13, based solely on arithmetics)?

I hope my question is not too stupid and I am not overlooking anything obvious. Thanks in advance for your kind reply.

2 Answers

+2 votes
by (6.2k points)
selected by
Best answer

This question is not stupid. I don't think that there's a way to exactly create a maximum value for variables. However, you could have a passage with the header tag with this code:

(if: $health > 10)[(set: $health to 10)]

As I said, It's not an exact way to set a max, but it works. Basically, if $health ever goes over 10 (so, if it got to 13), it would just set it back to 10.

by (180 points)
This is genius. Simple, but clever, and works like a breeze. Thank you very much, this solution is perfect for my project!
+1 vote
by (8.6k points)

Story JavaScript lets you do the following.

(function() {
	const testVal = Symbol();
	Object.defineProperty(State.variables, "health", {
		get: function() {
			return this[testVal];
		set: function(newVal) {
			if(!Number.isFinite(newVal)) {
				// ignore
			} else if(newVal > 10) {
				newVal = 10;
			this[testVal] = newVal;

As opposed to SugarCube, Harlowe doesn't mess this one up when switching passages. I have no idea what will happen on game save/load though.

by (159k points)

This solution relies on using an undocumented feature of Harlowe's engine to access it's story variables via Javascript, and may stop working if the Harlowe developer changes the implementation in a future version.

Because Twine 2 automatically updates all stories to the latest installed version of the selected story format and as new releases of Twine 2 may contain updated versions of included story formats then your project may stop working correct without notice if you install a later release of Twine 2.

by (8.6k points)
If you update your game development environment mid-development with no way to roll back, you're doing game development wrong anyway.
by (180 points)
Thank you for your answer. I went with the other one because it fitted perfectly to my architecture, but I appreciate your effort.
by (8.6k points)
@mishaland That's just how it is, not every answer will fit the requirements of the asker. Others might find it and consider it more useful though, so there's value in having multiple answers.

Don't forget to mark the other answer as "accepted" or "best" (or whatever this site calls the checkmark) though.
by (180 points)
@Akjosch Absolutely, I agree. And thanks for directing me to marking the answer, totally forgot.
by (110 points)
I'm very new to Twine and pretty green on JS too, so I would be thrilled to be able to do what you've done with this *undocumented* feature. I can only say that, not knowing otherwise, this seems like a possible solution to the frequently-criticized hardships of calling JS from Harlowe. Is there any way of putting in a vote for a particular feature in upcoming versions of Harlowe? I've been digging for a few days, looking for something like this solution, and it is not easy to find. I mostly have seen discouraging words from those who studied the problem. I suppose you found it by studying the sources? Is it as simple as it looks?

by (8.6k points)

@dkpstarkey I have no clue about Harlowe's development process or what's possible to request as a feature, sorry. Harlowe itself has a repository with its source code as well as "Issues" - usually they can be used to add feature requests, but that depends on the project's maintainer. Check it out if you like: https://bitbucket.org/_L_/harlowe