Closer Look: The Making of Quickhack

Previous Post
Next Post

Closer Look: The Making of Quickhack

May 10, 2017, 10:49 p.m.

"Maybe," I thought to myself, "I can make a game on a single board as my small world."

A dungeon crawl seemed like a good fit. Caves would work for a more natural maze layout, and by having everything on one board, I'd be able to get away with not thinking so much about level design because I'd have time to actually refine the board later.

It would also let me use a game mechanic that though well known as a possibility hadn't actually been used done in ZZT before: setting torch cycles.

Normally a dark room in ZZT requires the player to press the T key to light a torch, which sets your torch cycles to a certain amount, and decreases to zero before requiring the player to light a second torch. This is pretty annoying and combined with the issues of low visibility even in torchlight makes dark rooms relatively unpopular with later ZZT worlds.

Since the torch cycles remaining are stored when a game is saved, and saves and worlds are identical to ZZT, it's possible to set the torch cycles to 32767 and have a single torch which lasts for roughly 3276.7 seconds. This works out to a little under 55 minutes of torchlight without the player having to actually press the T key at any time.

A lot of ZZT games can be finished in an hour, but nobody ever used the technique since the torch cycles deplete on every board, meaning any time not spent in a dark room is wasting torch time. If the player ran out of time, they'd be out of luck since lighting any torches afterwards would only provide the normal amount of torch cycles.

Here however, since the entire game would be confined to a single board the time limit wouldn't be a problem, and there'd be no worries of any of it being wasted. Additionally the limited visibility would be a plus, allowing the player to still explore rather than have everything revealed as soon as the game was loaded.

I called the game Quickhack due to this time limit (even if it was generous) and because it would deliver the hack and slash gameplay of a dungeon crawler on a single board, making it pretty quick to play as well.

I first started by designing a tiny village. I wanted there to be an item shop, an inn, and some sort of hub for quests. The village was originally in the top left corner of the map, but it wasn't long before I realized that having to backtrack to the village for healing would make it more suited towards being in the center of the board.

Another early idea I had was for there to be classes the player could select. I would vary the player's maximum health, attack method, and even speed. The speed adjustment would be cut very early on as I quickly realized how impractical it would be. ZZT doesn't allow you to adjust the player's speed normally. Players always move at the fasted speed of cycle 1, meaning they act on every game tic. Starting a game or going through a passage causes the player on the destination board to be destroyed, and a new one spawned where they're needed, which will always be cycle 1 as well.

By confusing ZZT with bombs and conveyor belts, its possible to physically destroy the player object which is normally not possible.

The player handles all keyboard input, so ZZT will softlock when this happens unless there's another player element on the board (or an object places one). These other players can be of whatever cycle, so it would maybe be possible to engineer a scenario where the player begins the game on a conveyor with a bomb, gets destroyed by it, and then a slower moving player object would get to take over.

Trying to actually do this had its own share of problems. Firstly, the bomb and conveyor trick only seems to work if the player is also trying to move so it would be possible for the player to not be destroyed and break the whole thing. Secondly, the player handles its keyboard input only during its active cycles, which is normally all of them. A player at cycle 3 means input will only be read every 3rd cycle. This means moving, shooting, or even pressing the "S" key to save the game would basically have a 2/3 chance of being a dropped input entirely! Once I realized this would be the case I immediately scrapped the idea of adjusting the player's speed. I don't know if it would be possible to make a ZZT game with input that unresponsive and have it still fun to play.

So let's take a quick look at the three classes as they did get implemented:

Setup
  •    •    •    •    •    •    •    •    •
F I G H T E R
Fighters have trained with swords for
years. As masters of the blade they can
cut down foes who get close effortlessly,
and have the physical strength to stand
strong against powerful enemies.

Maximum Hit Points: 80
Weapon: Sword
  •    •    •    •    •    •    •    •    •

Firstly is the fighter. They use a sword engine that was also used in my previous Ludum Dare ZZT game, "Ruins of ZZT". An object loops checking for a bullet, and when it finds one, it waits a moment, then #changes the bullet into an empty space. The delay determines how far the bullet travels, and at small ranges, gives it similar behavior to stabbing at a close range with a sword.

I did feel a little guilty repeating this exact same mechanic a second time. It has a few drawbacks, since if the bullet is traveling over a fake wall or water when it's erased, the tile underneath is also destroyed, restricting use of these elements. Its biggest drawback, comes from the fact that there's no way with ZZT-OOP to tell if a bullet was shot by the player or an enemy. This prevents any enemies in the game from using bullets themselves as they would cause the timer for erasing bullets to no longer sync to player attacks, causing the sword to randomly have a shorter range than it should or even be erased the moment it is fired.

Fighters gain the benefit though of having nearly endless attacks and infinite use of them. They also have the largest maximum health which means they benefit from the inn's constant price for healing the most.

Setup
  •    •    •    •    •    •    •    •    •
M A G I C I A N
Magicians have dedicated to lives to
learning the secrets of arcane energies.
They are frail, but excel in ranged
magical attacks able to keep foes from
ever getting close to begin with.

Maximum Hit Points: 40
Weapon: Staff of Magic Missiles
  •    •    •    •    •    •    •    •    •

The second class is the magician. They were designed to have the infinite range of regular ZZT shooting, but with a limited amount of ammo to actually shoot with that regenerated slowly over time. I really like how this class came out since balance was pretty much a shot in the dark. They have the most interesting boss fights since they can't always be on the offense, needing to dodge the enemy long enough to recharge their mana/ammo.

Setup
  •    •    •    •    •    •    •    •    •
E L F
Elves are creatures of the forest and are
known for their skills with a longbow.
They are capable of launching a volley of
arrows, provided of course, they have
ammunition to spare.

Maximum Hit Points: 60
Weapon: Longbow
  •    •    •    •    •    •    •    •    •

The final class is obviously "Elf". I am forever amused by that being the class in the original Dungeon and Dragons and not "ranger" or "archer", and I wanted to use slightly more oddball class names, hence "magician" and not "wizard". Elves were more of an afterthought, and weren't added until about half the board was created. They use ZZT's shooting exactly as intended. You shoot arrows as rapidly as you want and as far as they can go, with the only limitation being have ammunition in the first place to be able to fire.

I was quite unsure what my goal with this class was. They were definitely the most difficult to balance, since fighters and magicians could never run out of ammo permanently. If an elf runs out of arrows during a boss fight, they're forced to game over. The need to buy arrows from the village also meant that gems were more essential. I considered just giving them a very large quantity of starting ammo and being a challenge class where they couldn't get more, but felt that wouldn't be all that fun.

The beta testers all had positive things to say about the class system, pointing out how you're not so much picking a weapon, but how to manage your ammo. There's basically a sliding scale of how easy it is to inflict damage with your weapon which is inverse to how limited you are with your ammo.

I did feel a little guilty recycling the sword from before, but would love to use this trifecta of combat styles again as I think it really added to the game.

The classes themselves went through plenty of changes themselves. At the last minute I began worrying about how difficult the game would be for those with little if any experience with ZZT and tweaked the numbers a bit. Every class got a max HP boost, from 60, 30, 40 to the current 80, 40, 60. For nearly all of the game's development, magicians only had 3 mana rather than 5. The regeneration rate also got buffed as well since I'd find myself standing outside a boss door waiting patiently for mana to refill before going in. Lastly the elf had changes to starting ammo. I considered some other potential buffs to the elf such as giving them some starting gold to be more comfortable with buying arrows, as well as giving them dark-vision as a way to automatically reveal any hidden treasures.

Starting with the village I began work on the item shop. I planned to offer healing potions, but also wanted to have other items to purchase that could be beneficial depending on the player's class.

Like the numbers for class stats, the shop's prices and potion effects were repeatedly changed throughout development. I wanted to make sure that healing potions could serve a purpose when the inn to restore health to its maximum was also right there. At 2 gems for 10 health, this made it cheaper to restore to full health by using the inn for all classes, but meant that partially injured players would have to weigh the risk of dying in combat, or spending their gems a little more inefficiently for the safety of topping off their health.

Fighters can more easily get away with not buying health potions, but a magician with 20 out of 40 hp has a tougher decision to make.

An issue I ran into when designing the potion shop, was that since the town was a hub, and the potions would take effect immediately, they had to have a benefit that would work without it mattering if a player half completed a section of the caves and needed to backtrack. The potions needed to provide a benefit that wouldn't be wasted by going through empty sections of the caves again.

I decided on a potion of regeneration which would heal the player over time meaning they could gain health while in combat, and to allow the potion's effects to not check the player's maximum HP when healing. This way a class could heal at the inn, then drink a potion to overheal themselves and be more prepared for their next fight.

The regeneration effect tries to strike a balance between being fast enough that the player does actually benefit from it, but slow enough that they won't want to drink a regen potion, idle in town, and drink some more. I didn't want a game called Quickhack to have a strategy of slowchug. The slow healing also means that fighters benefit from them more reliably, as a magician may get themselves killed before the next health increase with so little HP to spare.

While any class can buy healing or regeneration, the other two items for sale are exclusive to the other classes. Magicians get potions of boost mana which provide 15 ammo at once, letting them stack up before a boss fight and basically fight them like elves would. I think originally they only provided 5 extra mana. I also considered changing it so that they'd boost the regeneration speed of mana for a bit rather than just flatly give ammo, but I think the sudden burst lets the player strategize using them for bosses better.

Elves get to buy arrows. There's not much to that. The price for arrows and amount purchased varied wildly throughout development. If I were to go back I think to add more risk/reward to the elf playstyle I'd have options for larger bundles of arrows that would be more cost effective, but mean risking running out of ammo while you save up for a better priced bundle.

My first Ludum Dare ZZT world, "Ruins of ZZT", had a help board available from the start that explained some basic ZZT concepts to those who had never played any ZZT worlds before. I wanted to avoid having a menu this time to keep the number of boards down to as few as possible. So, in its place is the Tome of Sweeney. Tome Sweeney, a brilliant pun, is a help book. It doesn't really go on to explain what ZZT is and the sorts of things made with it, and just sticks to telling new players the controls and some advice, as well as cheats to turn off darkness as well as some special treasure hidden to make the game very easy to complete.

The tome itself wasn't done until the end of the game, since I wasn't sure how much space would be left. Instead, I opted to use an undocumented feature of ZZT, (though one that has been used by several people before,) which is the ability to have a hyperlink display an external file!

This was never mentioned as a feature in the ZZT help file, but was used in Town of ZZT itself to display an order form during gameplay. Rather than having something like !read;Read the scroll and a :read label to jump to with text afterwards, you can instead say !-scroll.txt;Read it. to tell ZZT to look for scroll.txt and display it instead. This has some use here and there as a way to save space, but does have issues where the file's contents are _not_ parsed as ZZT-OOP so you can't put code in additional files or even other hyperlinks.

I considered at first having more dialog throughout the game which would be displayed using these files, but opted against it since the game's plot wasn't really much of anything to begin with and with what little was there I was able to come in under the 20KB board size limit.

Hidden within a wall as mentioned by the Tome of Sweeney is a little cheat item I made sure to include so that anybody could be confident they could complete the game. The treasure is a ring of djinni summoning, taken from the roguelike ADOM which can be used to grant the player a single wish. While ADOM has the luxury of a text parser for this sort of thing, the possible wishes here are fixed. The player can get 5000 health and their max health limit removed; 5000 gems if they want to play through the game mostly normally, but without fear of getting themselves stuck; or they can take two class specific wishes.

Magicians can wish for infinite mana, which removes the check on maximum mana causing a magician's ammo to never stop rising. Elves can wish for 5000 arrows.

I felt like these kept the flavor of the game in mind as opposed to just giving the player 5000 or so of everything and calling it a day. There's still a choice to be made, though really any of them will radically simplify the game.

Lastly, is the village elder. They're used to explain the player's purpose in the caverns, recovering the mythical amulet of Nibor. As always in these sorts of games, the player first has to prove their worth with a simple quest.

The elder gives a quest to slay an orc chieftain whose tribe has been raiding the village. Your general level 1 adventurer sort of thing.

Okay! That's the village! Now we can get onto the rest of the game which is rather simple and shouldn't take too long!

Previous Post
Next Post