Egg Meister: My First Finished Playdate App

I created, or better yet finished my first Playdate app. I called it: "EggMeister." The first reaction from a friend was... you mixed English with German... I said, yup that's the gag. Anyway, what the app is about is boiling eggs! Why? Well, why not? I love boiled eggs on a nice weekend morning. Sadly, I got no time during the week. But maybe this app will bring hope in a new phase of my life. Earning money by creating niche apps for niche devices.

A brief history of my game dev experience

As I wrote some time ago, I was busy creating my first game on the Playdate. What happened? Well, I didn't finish it (yet). The project was bigger and more complex than I thought; it was my first introduction to game development. Well, not really; my first introduction was back in 1995 when I wrote a Lemmings clone in Turbo Pascal, including a level editor. Since Turbo Pascal had some memory issues, I had to create several executables: one for the intro, one for the game, and one for the outro. I have to admit that wasn't the first game I tried to program. Six years earlier, I tried it on the Commodore 64. Yes, again a Lemmings clone... and no, it was not the first; the first was on a ZX-81. I was something around... I don't remember... 8? You got a book with code, and if you typed it into the ZX-81 in agony for an hour, you finally got a game in ASCII graphics of a block on a fictive road. I noticed that when you changed the code, you could make it more difficult or easier... Also, other characters as obstacles made it even more fun. Anyway, that's about how far my fascination with game development went. Now, in the days of indie development, I gave it a new try, and since I was a fan of the Game Boy, it seemed like a dream come true to create my own Game Boy / Playdate game. I truly think that the Playdate is a modern version of the Game Boy crossed with Teenage Engineering's out-of-the-box design.

The research

If you search online for a formula to calculate boiling times, you'll likely find Dr. Charles D. H. Williams from the University of Exeter. He has a webpage on the science of boiling eggs, including a PDF with the full formula. The cooking time t (in minutes) for an egg with mass M (in grams) depends on the starting temperature of the egg Tegg, the water temperature Twater, and the desired yolk temperature Tyolk  (all in °C). The formula looks something like this:

Then I also found a second formula produced by Braham:

Barham's formula calculates the time for the center of the yolk to reach a specified temperature, Tyolk, while Williams' formula calculates the time for the yolk-white boundary to reach the same temperature. Although it's unclear if the formulas differ fundamentally in this aspect, a comparison of both formulas for 50 eggs shows they are similar for Tyolk = 63 C and Twater =100 C, except for a larger spread in circumference measurements. For higher Tyolk or lower Twater, Williams' formula results in longer cooking times than Barham's. Since I want to use grams as an input, Williams' formula is more practical for my needs, as Barham's formula does not accommodate this input effectively.

The doneness of an egg depends on the temperatures of the white and yolk. Egg white starts to firm up between 62-65°C due to a protein called ovotransferrin. The main protein, ovalbumin, doesn't firm up until 80°C. The yolk begins to thicken at 65°C and sets at 70°C. Heating to 80-90°C gives the yolk a crumbly texture, typical of hard-boiled eggs (source: https://khymos.org/2009/04/09/towards-the-perfect-soft-boiled-egg/).

Temperature / °C Egg white Egg yolk
62 Begins to set, runny Liquid
64 Partly set, runny Begins to set
66 Largely set, still runny Soft solid
70 Tender solid Soft solid, waxy
80 Firm Firm
90 Rubbery solid Crumbly texture

From this table I generated the following settings:

Type Temperature / °C
Soft 64
Medium 71
Hard 80

I ended up with adding 1 °C to the medium setting to make the white a bit more tender and solid. But of course, after the release I am open for any comments and recommendations.

Developing the prototype

I used the Noble Engine as the base and added some extra libraries on top, called my “Mr. Bot Core Libraries.” These handle tasks like interaction, inputs, sprites, FX, sounds, etc. Basically, I only use the Noble Engine for the structure and scene transitions. Once I set up all the necessary requirements

First of all I started to design the Dialog Screens:

For Selecting the egg temperature:

Selecting the egg size:

And for the egg hardness:

Then I wanted a set of digital LCD numbers, and an egg with a yolk that would pulsate while cooking. I mainly used Aseprite and Pixquare (for on-the-go) as tools to create some pixel art. For photos, like my kitchen tiles that I later used as a background for the settings, I used Photoshop to reduce the colors to 1-bit. It's important to adjust the brightness, contrast, shadows, and highlights accordingly so that the 1-bit version looks nice in the end.

I wanted to try something new for the "unselected" version in the settings, so I thought of using the Playdate SDK function:

image = Graphics.image.new('image_file')
image:fadedImage(0.4, Graphics.image.kDitherTypeFloydSteinberg)

In all my semi-transparent sprites, it works like a charm. I used this technique for the pause menu as well. The main goal of using these effects is to reduce the size of the finished game. Since I don't need to store the semi-transparent option, adding or changing an image costs only one image instead of two. I am a bit of a perfectionist when it comes to reducing bytes and compressing. For all my images, I used tools like TinyPNG to significantly reduce the sizes of the PNG files.

I also wanted to add a small gimmick to the app and thought of doing something with the crank. So, I added a small game that pops up when you pull the crank out during the countdown.

The game has a kitchen background, and the user controls a pan at the bottom using the crank. The goal is to catch the dropping eggs. For every egg caught, the user earns points, depending on the difficulty level. Of course, it shouldn't be too much of a focus, because after all, the main goal of the app is an egg timer. The timer should also be visible in the upper-left corner - we don't want to ruin the boiled eggs! Anyway, I wanted to design the game so that it starts easy and gets more difficult over time. I first tried a version where the difficulty increased after every 10 egg drops, but then I thought, "Maybe it's more fun if the difficulty increases after every 10 egg catches." However, I wasn't satisfied with that result either. Then it occurred to me: the game should measure its difficulty based on the time left. So, I took the total time, segmented the game into 100 levels, and calculated the player's level based on the time left. There are two things that will increase as time passes by: the dropping speed and the spawning speed.

Adding some sound

Every game or tool needs some sound! The sounds I created for EggMeister were all made with Reason. Yes, I am from that generation, but I have to admit that Reason has changed a lot since 2000. It used to be a tool for creating music and beats without the option to record music within the DAW. Nowadays, you can do everything with it... Finally!

So, I had to find some appropriate sounds for my app. I tried various synthesizers, effects, and even started to create a tune for the app. I wanted it to be a chill, lounge-style background sound, and since music production is a significant part of my life, it was only fitting to create a track for the app. As soon as you open the crank and the game starts, the sound should be a bit louder, with more bass and a beat, giving you the feeling that you're in game mode. When you dock the crank again, the sound should seamlessly transition back to the previous chill theme song. It took a while to get this part just right, but I'm quite happy with the solution. The only downside to adding music to the app is that it increased the app package size from 1.2 MB to over 7 MB. I compressed all my sounds using the following command:

ffmpeg -i input.wav -acodec adpcm_ima_wav output.wav

I want to keep the track in a loop of about 1 minute so that it has enough variation. So the only way to reduce it is to make the music mono. Since the Playdate without headsets is anyway mono and an egg timer with headsets is not the usual scenario, I changed the tracks to mono. In that way, I reduced the file size back to 3.2 MB. I think that is a reasonable size for an egg-ready countdown app. Although I am not entirely happy with the mono sound, somehow the stereo sounded better. I need to put some more research into that part; maybe removing some echo makes it more solid.

Testing the prototype

I cooked my first egg with the Playdate and noticed that the egg wasn't as soft as I wanted it to be. The time was correct, so maybe the timer was out of sync? For timer testing, I used a stopwatch that I started as soon as I started the countdown of the app. It was out of sync. For the countdown, I used a timer object from the Playdate SDK. Somehow, it didn't work as I had hoped. A 5-minute countdown ended on the Playdate in 5 minutes and 15 seconds. Now probably the reason is that some processing takes a few milliseconds that gets added to the 1000 milliseconds timeout. Never thought about it that it would cause a 15 seconds impact.

Now, I can do two things: adjust the timeout to a tick less and hope that it matches, or take a completely different approach and use the timestamp to check if a second has passed. The second option is less performant and probably less energy-efficient since it has to do the check in the update function, which runs at a frame rate of 30 times per second. However, I think it is the most accurate way to keep the timer in sync with an actual second passing by. While developing, I didn't test for longer than 10 seconds in most cases... that's why the issue occurred earlier. And as a programmer, you would think that a one-second timeout is a one-second timeout. That's why it's always important to test the real thing.

I thought I was finished, but sadly, I was not. The sizes I used were the European standards. I discovered that every country or continent uses different sizing systems. To simplify matters, I decided to reduce the sizes to the four most commonly used ones and focus only on major countries or continents. For now, I am considering the US, Canada, Europe, Australia, New Zealand, Brazil, Japan, and South Africa.

To get more feedback, I gave a copy to my brother so he could test it and let his kids play the tiny game; they seemed to love it.

As feedback I got that the game gets too difficult and if it would be possible to enter some specs other than the default ones. This resulted in a new option on the "Locations" scene, now you can select "Customize" that gives you the option to select the egg temperature and mass.

Finalizing

Finally, I got everything that I would like the app to be. I made it even possible to add new functionalities like egg cooking times and additional alarm sounds and even gave it a customization option. The app has various settings like altitude and egg temperature settings, and the whole thing is even backed up with a scientific egg cooking formula... all these parts make it a perfect egg cooking tool.

Egg Meister is coming to the Playdate Store!

I am excited to announce that "Egg Meister" is coming to the Playdate Store! Woooooop Woooooop 🎉

If people want to discuss the app or have questions or ideas on how to make this app even better, please don't hesitate to contact me by mail: help@mrbot.de or write to me on the Fediverse: @dev@mrbot.de.