Setting Up OpenFL and MUnit To Use Test Driven Design in Games


I recently discovered the Haxe language, which when combined with with OpenFL, can produce some pretty great things (for example, Papers, Please was developed with Haxe + OpenFL). I’ve also been reading about Unit Testing and Test Drive Development and how it can greatly improve not only the quality but also the efficiency of the code you write. This seemed like a perfect opportunity to learn some new things, so I’ve decided to start developing some games using TDD in Haxe!

Before I could do that, however, I had to figure out how to get MassiveUnit (munit) set up, which was a bit trickier than I was expecting. Hopefully this guide will help others who stumbled with the process!

For this quick tutorial I’ll be using FlashDevelop. I was initially rather hesitant to use FlashDevelop instead of my usual Sublime Text, but it’s Haxe-specific development features won me over in the end.

Once in FlashDevelop, create a new OpenFL project:

Then open up a new command prompt, and install munit if you haven’t already:

haxelib install munit

I find it incredibly handy to use a set of (modified) FlashDevelop macros to set up and use munit. The modified macros I use are shown below. To set up these macros, press Ctrl + F10.

LabelMacro Entry
mUnit - InitializeRunProcess|cmd.exe;/c cd "$(ProjectDir)" & haxelib run munit config -reset
mUnit - Run All TestsRunProcessCaptured|$(SystemDir)\cmd.exe;/c cd "$(ProjectDir)" & haxelib run munit test -coverage
mUnit - Add Testcase For Current FileRunProcessCaptured|$(SystemDir)\cmd.exe;/c cd "$(ProjectDir)" & haxelib run munit create -for $(TypPkgName)
mUnit - Generate Test SuiteRunProcess|cmd.exe;/c cd "$(ProjectDir)" & haxelib run munit gen

Once you have the macros set up, go ahead and run the Initialize macro. This will open a command prompt that gives you a bunch of options. The defaults are ok, so just press Enter for each of them until they go away.

munit will then create some folders and files in your project directory:

ExampleTest.hx is just a sample test case with a couple basic tests which will pass without issue. TestMain.hx is the main() function that will be called with you run the unit tests—you can safely ignore this file. TestSuite.hx is a quasi-auto-generated file which runs your various test cases. When you run the Generate Test Suite macro, this file will get updated to reflect all of your testing cases / classes.

The file you most have to concern yourself with is the test.hxml file which will have been dropped into root file. It probably looks like this:

## Flash 9+
-main TestMain
-lib munit
-lib hamcrest
-cp src

-cp test
-swf-version 11
-swf build/as3_test.swf

--next

## Flash 8
-main TestMain
-lib munit
-lib hamcrest
-cp src

-cp test
-swf-version 8
-swf build/as2_test.swf

--next

## JavaScript
-main TestMain
-lib munit
-lib hamcrest
-cp src

-cp test
-js build/js_test.js

--next

## Neko
-main TestMain
-lib munit
-lib hamcrest
-cp src

-cp test
-neko build/neko_test.n

--next

## CPP
-main TestMain
-lib munit
-lib hamcrest
-cp src

-cp test
#-D HXCPP_M64
-cpp build/cpp_test

If you were to try running a test right now, you would run into an issue:

src/Main.hx:3: characters 7-27 : Class not found : flash.display.Sprite

This is because the required OpenFL libraries aren’t defined in the test.hxml file. Thankfully this is a relatively easy fix. First up, I delete everything that isn’t Flash 9+ so that test.hxml looks like:

## Flash 9+
-main TestMain
-lib munit
-lib hamcrest
-cp src

-cp test
-swf-version 11
-swf build/as3_test.swf

Next, add the OpenFL and Actuate libraries:

## Flash 9+
-main TestMain

-lib openfl
-lib actuate

-lib munit
-lib hamcrest
-cp src

-cp test
-swf-version 11
-swf build/as3_test.swf

And voilà! Running the test should open your browser to a page that looks like this:

Of course the two tests passed—they were `Assert.isTrue(true);` tests!

If you run into any issues, press F8 to compile your project normally, then inspect the bin/flash/haxe/debug.hxml file to see what the major differences are, and add them to the test.hxml file.

There’s just one last thing required to properly get up and running writing tests: adding the munit library to the project so that you can get code-completion on munit’s API. Open application.xml and add the line <haxelib name="munit" /> to the classpath, haxe libs section so it looks like:

<!-- classpath, haxe libs -->
<source path="src" />
<haxelib name="openfl" />
<haxelib name="actuate" />
<haxelib name="munit" />

Voilà—for realsies! If you want to add a test case for a specific class (which isn’t a bad idea in order to keep your tests reasonably organized), just open the file in FlashDevelop then run the Add Testcase For Current File macro. This will create a corresponding [class]Test.hx test class for you to populate. Note that before you run any tests, you’ll want to regenerate the test suite by running the Generate Test Suite macro.

Good luck, and happy test-driven-development! If you run into any issues, feel free to comment below and I’ll see what I can do to help you out!

Join me next time for when I start developing an entity-component game engine in Haxe using munit for test-driven-development!

Real Time Analytics