Rebuilding Hayaku in Unity, one tool at a time

Hello again. In the first post, I talked about why we’re moving Hayaku! Island of Darkness from Construct to Unity. This time, as promised, I want to show you a little of what that work involves.

FIRST I bring them in showing how the game looks and feels and the awesome mechs and THEN once I got them I unleash all my boring technical talking points about tools and importers BWAHAHAH

There are two parts to that story. One is what Unity lets us do with the game. The other is all the stuff we’re building inside Unity to help us do it.

Why Unity

Construct deserves a lot of credit. Hayaku! exists because it gave Ezequiel, an artist with almost no programming background, a way to build a game by himself. Then the game grew, the team grew around it, and we needed an engine that fit the project Hayaku! had become.

For Martin and me, C# is a much better language for working on a game this size. We can organize the code, understand how its parts depend on each other, and change one system without having to perform archaeology on an event sheet from five years ago. We still perform archaeology, obviously. We just have better equipment now.

Hayaku also runs better in Unity, and we have better ways to understand why when it doesn’t. We can profile the game, find what is actually taking time, and work on that instead of blaming whichever system looks suspicious today.

Then there’s how it looks. Unity’s Universal Render Pipeline (URP) gives us a lot of room for the visual nonsense we love. We can write custom shaders and renderer features. Our effects can get much more dramatic while still respecting Hayaku’s pixels. We can even make the entire game look like it’s running through a CRT or a Game Boy screen, because apparently giving ourselves one art direction wasn’t enough.

The same game, three different lies about the screen it's running on.

The Unity Editor may be my favorite part of this, though. We can extend it. When a recurring job becomes slow or annoying, we can build a window or a button that understands Hayaku specifically. That’s how we ended up with tools for importing levels, editing the map, writing dialogue, working on quests, testing cutscenes, understanding how the levels fit together, placing stuff… The list is endless.

Unity gave us room to make Hayaku more ambitious, and then gave us ways to improve how we make it. I’m honestly grateful that a team our size can build this much on top of the engine.

The port itself is still an unreasonable amount of work. One of our tools started with the part I was most desperate to stop doing.

Please don’t make me place all those tiles again

A lot of Hayaku! levels are made from tiles: small pieces of an image arranged on a grid. Put them together and you get the walls and floors of a room. Keep going, add more rooms, and you have a level.

You can reproduce all of that by hand. I know because… well, because at this point I had already built (ported, actually!) a couple of rooms that way. A couple was enough to never want to copy the tiling again.

Placing tiles when you’re designing a place can be fun. You’re trying a jump and moving a platform because it doesn’t quite work. Copying a room that already exists is such a drag. The decisions are already there in the other engine. You just have to put everything in the same place again. Mind-numbing, time-consuming, tedious as all hell. Boring.

So I wrote something to do that part for us.

The idea was to read the level data saved by Construct, find which tile belonged in each position, and place the matching tiles in Unity. All those decisions Ezequiel had already made were inside the project files. I needed the importer to understand them.

Sounds easy. I thought it would be.

SPOILERS, I guess: it wasn’t.

Construct has its own way of saving which tile goes where in a JSON file. The actual data looks something like 23x0,4x85,15x0,14x85,62x0..., which is very useful if you already know what all those weird numbers mean. Imagine… oh, I don’t know. ~650k of those numbers? Give or take.

I did NOT know what those numbers mean.

I had to figure out that weird robot language and get the math right to translate every position. You see, Construct and Unity don’t agree on which way is up. Or even, what zero is. There was a lot of research and trial and error… and I mean A LOT of trial and error. I kept changing how the importer read the data (it brought… I don’t know, it brought SOMETHING. Not anything that made sense, but something), changing the calculations, and trying another import. And another. And one more. And then another. And so on and so forth.

By then, we had movement and jumps working, a couple of enemies, and those rooms I’d made by hand. And on the attempt number one thousand five hundred and thirty seven, I imported a whole level and suddenly it MOSTLY LOOKED RIGHT.

Oh wow. What a feeling.

Only the shape had come over that first time: the walls and floors. Or, to be completely accurate, everything had come over and EVERYTHING WAS A WALL. But I could recognize the whole level, and I hadn’t just spent my time copying it tile by tile. I mean… I HAD spent the time making this work. But this was going to save.

SO.

MUCH.

TIME.

IT WORKED! Mostly.

I was very happy with mostly.

It’s been many months now, and the tool does a lot more. We can choose a level and the tile layers we want to bring over, including the decorative ones. A transparent preview shows where they’ll land, so we can check the placement before importing.

The importer today: check where the tiles will go, then bring them over.

Getting from that first success to a room that looked and behaved like Hayaku took much more work. Backgrounds and decorations came next. The camera needed its own attention, including a custom parallax system that keeps our pixel art flat and crisp while giving the scenery depth. We made its settings work like the ones Ezequiel already knew in Construct, because yeah changing engines was enough disruption for one artist.

Construct on the left, Unity on the right. There was plenty of hand work between these two pictures.

MOST of the port had to be done by hand anyway. The importer gets one particularly boring part out of the way. That is enough to make it one of my favorite things I’ve built for the game.

Ezequiel will correct this

Cutscenes have their own tool: a little language we write in text files.

Think of them as screenplays.

A script can tell a character to walk somewhere and wait. It can move the camera, play an animation, or start a conversation. We write the actions and their timing, and the game performs them. A very small screenplay with unusually specific opinions about how long walking should take.

My first pass is mostly about making the scene functional. The characters do what they have to do when they have to do it. Then Ezequiel corrects them.

A character can arrive in exactly the right place at exactly the right time and still look weird doing it. A short pause can make a reaction feel right, or make everyone look like they forgot why they’re standing there. We need to keep watching the scene and changing it.

Because the cutscene lives in text, we can edit it and trigger it again in the Unity Editor without restarting the game every time. That removes a huge amount of waiting between having an idea and seeing whether it works.

A piece of script, and hayaki and the tenebris follow their instructions. Timing subject to Ezequiel.

There’s also a less profound reason for using text files: I prefer working with the keyboard. The mouse is so much slower for this stuff. Please don’t make me reach for it just to change a number.

The map takes some liberties

The map tool solves a different problem. It starts with the real rooms in our levels and gives us a map generated from that data.

Then we adjust it by hand, because the game has a very particular idea of what a room is. Often, it’s a rectangle that tells the camera where it can move.

You, presumably (and hopefully!, should be experiencing something more interesting than a collection of camera rectangles.

A passage that turns into a drop can feel like one L-shaped place, even if the camera needs separate areas to handle it. The map should help you recognize the place you walked through. Showing you the camera’s filing system would be a strange way to do that.

So the map editor lets us group those spaces and reshape their outlines. The rooms come from the actual game, but we can change their proportions and connections until the whole place is understandable.

The rooms are real. Their proportions are... let's call them 'negotiable'.

We still have a lot of road ahead of us, but we’re moving faster than ever now, and so we can start to fathom when we might start to see the endline in the far distance.

If you liked this look behind Hayaku, let us know. Honestly, I’m not sure if this has an audience (Lengthy blog posts? In 2026?? And on top of all… I’m getting technical in them???) We have lots more tools, and each one comes with another story about a problem we were tired of solving by hand. If people want to read those stories, I’ll happily write more of them.

Yeah, this was always going to be here… WISHLIST PLZ

If Hayaku looks like your kind of game, add it to your Steam wishlist. It helps us, and you’ll hear when it’s available. Win-win.

Already wishlisted it? Tell a friend… or several. You can send them this post, the trailer, or one of the mecha GIFs if you think that will do a better job. I won’t be offended. I’m not dumb. I even started this post with a GIF.

There’s more of the game on Ezequiel’s Twitter, and our Discord is open if you want to hang around while we make the game.

Thanks so much for reading. Like and comment if you want more of the technical stuff!