Sharing My Solution to a Heart-Based Health HUD

I also posted this on Reddit but I hoped it would be helpful to anyone browsing these forums as well.

I created a HUD for Twine 2 in Harlowe 3 that displays health with hearts similar to The Legend of Zelda, The Binding of Issac, etc that can be modified to display whatever symbol you want using a Full-Health Point > Half-Health Point > Empty Container system.

TEST
<!-- Set Initial # of Health Points and Current Health -->
{(set: int-type $maxHearts to 5)
(set: int-type $health to 7)
(set: int-type $maxHealth to $maxHearts*2)

<!-- RenderHealth: Calculate Array containing the Health Points -->
<!-- Calculate # of Full Health Points based on Current Health Points -->
}|RenderHealth>[{
	(set: int-type $nth to 
		(cond: $health % 2 is 0, $health/2, ($health-1)/2))

	(set: $hearta to 
 	 	(repeated: $maxHearts, "∙ "))
	(if: $nth < $hearta's length)[
		(set: $hearta to (repeated: $nth, "🤍 ") + (subarray: $hearta, $nth+1, $hearta's length))
	]
	(if: $nth is $hearta's length)[
 	 	(set: $hearta to (repeated: $nth, "🤍 "))
	]

<!-- If Current Health is odd, replace the first empty Health Point container with a Half=Health Point -->
(if: $health % 2 is 1)[
	(set: _find to '∙ ', _replace to '♡ ')
	(set: $hindex to 0, $found to false)
	(for: each _element, ...$hearta)[
		(set: $hindex to it + 1)
    	(if: _element is _find and not $found)[
		  (set: $found to true)
		  (set: $hearta's ($hindex) to _replace)
	    ]
	]
]
}
Current Total Health: $health
Maximum Hearts: $maxHearts
Maximum Potential Health: $maxHealth
<!-- Output modified array as a string -->
(str:...$hearta)

Add Hearts | Remove Hearts
Add Health | Remove Health
Full Health
{
(Click: "Add Hearts")[
	(if: $maxHearts <8)[
		(set: $maxHearts to it+1)(rerun:?RenderHealth)
		]
	]
(Click: "Remove Hearts")[
	(if: $maxHearts >3)[
		(set: $maxHearts to it-1)(rerun:?RenderHealth)
	]
]
(Click: "Add Health")[
		(if: $health < $maxHealth)[
			(set: $health to it+1)
			(rerun:?RenderHealth)
		]
]
(Click: "Remove Health")[
	(if: $health is not 0)[
		(set: $health to it-1)(rerun:?RenderHealth)
	]
]
(Click: "Full Health")[
		(set: $health to $maxHealth)(rerun:?RenderHealth)
]
(if: $health is 0)[(show:?gameover)]}
]
|gameover)[You died!]

Preview:

HTML File:
Dropbox Link

Thank again to Greyelf for helping me both here on and Discord!

3 Likes

Well done!

Some of that code looks surprisingly familiar… :slight_smile:

note: you don’t need to assign the int-type data-type when you initialise those first series of variables.