Haxe 3, OpenFL, Arch, Android

haxeTom and I went through and installed Haxe 3 and OpenFL on our machines today.  OpenFL is the updated Haxe 3 version of NME.  These are a few notes, updating from my Haxe 2 comments, some of which are still applicable. All in all, the process seems smoother than it was for Haxe 2/NME on Arch… I’m excited!

Haxe

First install Neko out of the AUR:

sudo packer -S neko

Then Haxe 3:

sudo packer -S haxe

Note that you can do those two steps at once. If you receive an error about an incorrect Neko package version, it’s because the Haxe package doesn’t denote the version dependency. Running them separately as above will force Neko to be updated first, and then Haxe.

At this point you should setup haxelib:

haxelib setup

Tom sets the haxelib location to be in his home directory, which is most proper. I leave it in the default /usr/lib/haxe, for no good reason. In that case you need to modify the install directory to be owned by your user:

cd /usr/lib/haxe
sudo chown -R joe .

OpenFL

Next, install OpenFL following their instructions:

haxelib install openfl && haxelib run openfl setup

When it asks for sudo permission, it’s installing a simple script aliasing haxelib run openfl to just openfl, so you can skip it if you wish.

Now set HAXE_STD_PATH:

export HAXE_STD_PATH=/opt/haxe/std

After that you should be able to create and run a demo:

openfl create DisplayingABitmap
cd DisplayingABitmap
openfl test linux
openfl test flash
Success!

Success!

Android

Next, try to set up OpenFL’s Android support:

openfl setup android

That script will pull down the Android NDK, SDK, Apache Ant, and Java, but if you already have all that installed simply say no to each download request and enter the path manually.  You can then try to build a sample:

openfl create DisplayingABitmap
cd DisplayingABitmap
openfl test android

If you’re using a recent 64 bit android NDK, that will fail with a root cause of not finding g++:

sh: arm-linux-androideabi-g++: command not found

To begin with, in your haxelib directory, edit build-tool/BuildTool.hx. Specifically, the Linux parameter by line 1355 in the Android block should be altered from just the value linux-x86 to the following:

m64 ? "linux-x86_64" : "linux-x86"

The block will then look like:

      else if (defines.exists("android"))
      {
         defines.set("toolchain","android");
         defines.set("android","android");
         defines.set("BINDIR","Android");
         if (!defines.exists("ANDROID_HOST"))
         {
            if ( (new EReg("mac","i")).match(os) )
               defines.set("ANDROID_HOST","darwin-x86");
            else if ( (new EReg("window","i")).match(os) )
               defines.set("ANDROID_HOST","windows");
            else if ( (new EReg("linux","i")).match(os) )
              defines.set("ANDROID_HOST",
                          m64 ? "linux-x86_64" : "linux-x86");
            else
               throw "Unknown android host:" + os;
         }
      }

That last ANDROID_HOST setting is what matters; as shipped, it does not point to the 64 bit toolchain correctly.

Then in build-tool/android-toolchain.xml, edit the toolchain version to 4.6. Edit line 7 setting TOOLCHAIN_VERSION as follows:

<set name="TOOLCHAIN_VERSION" value="4.6" unless="TOOLCHAIN_VERSION" />

In build-tool/ then run:

haxe Compile.hxml

OpenFL, specifically openfl-tools, defaults to Android API 8. If you have that installed, you should then be able to build the OpenFL samples for Android. You will though need to stipulate 64 bit hxcpp:

openfl test -DHXCPP_M64 android

To change the target Android API, in your haxelib directory edit openfl-native/1,0,6/templates/android/template/build.xml and change the target property on line 7, e.g., from:

  <property name="target" value="android-::ANDROID_TARGET_SDK_VERSION::"/>

To:

  <property name="target" value="android-16"/>

OpenFL should then build, push, and run the target on your phone using this API version, stipulating the 64 bit toolchain as above. Hooray!

Success on my S3!

Success on my S3!

Installing Haxe/NME on Arch Linux x86_64

haxeSome updated notes on Haxe 3 and OpenFL are now available.

I love Haxe and NME.  But they’re at times not the most pleasantly packaged of software.  There are some definite lapses in checking the released versions for packaging problems, the nightly snapshots often have problems, and few of the setup scripts will work if you’re not using an apt-based system (i.e., Ubuntu). Having just installed on two 64bit machines running Arch Linux, the following are some notes on getting it all to work.

Flash Player

You’ll have to install the 32bit multilib stuff in order to install the Flashplayer standalone debug player.  You definitely want this as the debug player seems to be the only way to get reports on null pointers and such in your Flash programs.

Enable the multilib repository by editing /etc/pacman.conf to uncomment:

[multilib]
SigLevel = PackageRequired
Include = /etc/pacman.d/mirrorlist

Then udate the repo DB and install the multilibs:

sudo pacman -Syu
sudo pacman -S gcc-multilib

Accept everything pacman asks in running that command. Then install the player.

sudo packer -S flashplayer-standalone-debug

Haxe/NME Toolchain

The Haxe/NME stack includes a number of components. You could try installing these from the NME install script, but it’s based on Ubuntu and several components won’t work even after you adjust for that. Instead you need to cherry pick some parts and replace others.  The rest of this sort of follows the script, but injects some variations and other steps.

The first thing to install is Neko. You want to do this from the AUR package, e.g.:

sudo packer -S neko

Installing from the tarball like the NME script does will result in a broken dependency with libpcre3. Manually compiling from source to fix that seems to be a rathole, and using the AUR package seems cleaner than jury-rigging a .so fix.

Next is Haxe itself. Tragically, you seemingly don’t want to pull this from the AUR package. I haven’t looked at it closely to confirm, but believe it pulls from SVN, which often leads to problems. Today on installing from that I get errors along the lines of “Missing Standard library.” (not an exact quote). Instead, download the stable release and patch up an install:

wget -c http://haxe.org/file/haxe-2.10-linux.tar.gz
tar xzvf haxe-2.10-linux.tar.gz
sudo mkdir -p /usr/lib/haxe/lib
sudo chmod -R 777 /usr/lib/haxe/lib

sudo cp -r haxe-2.10-linux/* /usr/lib/haxe
sudo ln -s /usr/lib/haxe/haxe /usr/bin/haxe
sudo ln -s /usr/lib/haxe/haxelib /usr/bin/haxelib
sudo ln -s /usr/lib/haxe/haxedoc /usr/bin/haxedoc

haxe /usr/lib/haxe/std/tools/haxelib/haxelib.hxml
sudo cp haxelib /usr/lib/haxe/haxelib

haxe /usr/lib/haxe/std/tools/haxedoc/haxedoc.hxml
sudo cp haxedoc /usr/lib/haxe/haxedoc

sudo haxelib setup /usr/lib/haxe/lib

wget -c http://www.haxenme.org/builds/hxcpp-2.10.3.zip
sudo haxelib test hxcpp-2.10.3.zip

Finally, install NME and friends.  Begin with the basic download.

sudo haxelib install nme

From here I have tremendous problems.  Nothing will actually work yet, including the rest of the setup process; I simply get errors from tls.ndll about missing libopenssl.so.0.9.8. Seemingly there is a persistent problem in the packaging of NME such that it’s not properly searching the appropriate 64/32 bit Neko libraries. At this point you’re standing on the edge of a huge rathole. Compiling NME from source seems to be fairly complex to setup outside of the assumed Ubuntu environment. Installing that version of OpenSSL doesn’t work because it’s 32 bit. After repeatedly screwing around with this at length on several major releases of NME, short of setting up NME from source I don’t think you have any option here but the ugliest:

cd /usr/lib
sudo ln -s libssl.so.1.0.0 libssl.so.0.9.8
sudo ln -s libcrypto.so.1.0.0 libcrypto.so.0.9.8
cd -

Now you can continue installing and hope you haven’t just set some lurking booby trap to slam you on some other project months down the road…

sudo haxelib run nme setup
sudo haxelib install actuate
sudo haxelib install svg
sudo haxelib install swf

At this point things should work. However, I had trouble getting some of the RocketHaxe demos to compile with NME 3.5.4. It produced inscrutable and inexplicable errors about exceptions creating the output files. Updating to 3.5.5 seemed to fix these; I have no idea what else it broke in return. You can upgrade to a nightly build by downloading a new version from the NME builds repository. Then have haxelib switch to that version, e.g.:

sudo haxelib test nme-3.5.5-165-g354e1e6.zip

Test

Now you should be able to test everything out. Go into a random temporary directory and build a sample program:

nme create Addingtext
cd AddingText
nme build project.nmml flash
flashplayerdebugger Export/flash/bin/AddingText.swf

If that works, it works. If it doesn’t… Slaugther a chicken and call a priest or something. Please leave any comments you have about improvements to this process or other notes. Thanks!

Further notes about setting up Haxe for Android development are here.

Haxe/NME Android on Arch

These are some notes, the tricky parts mostly from tom5760, on building Haxe/NME apps for Android.

First install Ant and Java using the standard tools. Despite various warnings around, I have not had a problem using Java7 (OpenJDK).  Then install the Android tools using the AUR packages android-sdk android-sdk-platform-tools android-ndk. I use packer, so it’s as simple as:

$ sudo packer -S android-sdk \
                 android-sdk-platform-tools android-ndk

After that you need to use the android manager to install support for your API and device targets, like usual.

Next configure NME with the right paths by running nme setup android. Note that you need to do this as your user, not sudo. Opt not to download any of the packages. If you did a standard install you should have JAVA_HOME and ANT_HOME set for it to detect, but these are the standard paths:

  • SDK: /opt/android-sdk
  • NDK: /opt/android-ndk
  • Ant: /usr/share/apache-ant
  • Java: /usr/lib/jvm/java-7-openjdk

After that, projects still won’t compile. You’ll probably get errors like this:

Creating hxcpp.h.gch...
[ huge compile command... ]
/usr/lib/haxe/lib/hxcpp/2,10,2//include/hxcpp.h:13:20: error: typeinfo: No such file or directory
In file included from /usr/lib/haxe/lib/hxcpp/2,10,2//include/hxcpp.h:170: /usr/lib/haxe/lib/hxcpp/2,10,2//include/Array.h:195:21: error: algorithm: No such file or directory
In file included from /usr/lib/haxe/lib/hxcpp/2,10,2//include/hxcpp.h:162: /usr/lib/haxe/lib/hxcpp/2,10,2//include/hx/Object.h: In member function 'void hx::ObjectPtr::CastPtr(hx::Object*)': /usr/lib/haxe/lib/hxcpp/2,10,2//include/hx/Object.h:143: error: must #include before using typeid
In file included from /usr/lib/haxe/lib/hxcpp/2,10,2//include/hxcpp.h:170: /usr/lib/haxe/lib/hxcpp/2,10,2//include/Array.h: In member function 'void Array_obj::sort(Dynamic)': /usr/lib/haxe/lib/hxcpp/2,10,2//include/Array.h:388: error: 'sort' is not a member of 'std'
In file included from /usr/lib/haxe/lib/hxcpp/2,10,2//include/hxcpp.h:171: /usr/lib/haxe/lib/hxcpp/2,10,2//include/Class.h: In function 'bool hx::TCanCast(hx::Object*)': /usr/lib/haxe/lib/hxcpp/2,10,2//include/Class.h:139: error: must #include before using typeid
Called from ? line 1
Called from BuildTool.hx line 1301
Called from BuildTool.hx line 567
Called from BuildTool.hx line 604
Called from BuildTool.hx line 738
Called from BuildTool.hx line 767
Called from BuildTool.hx line 162
Uncaught exception - Error creating pch: 256 - build cancelled
Error: Source path "bin/android/obj/libApplicationMain.so" does not exist

These are caused by Haxe/NME not locating the NDK libraries correctly. Recent versions of Android reorganized the directory structure a bit, so you have to do this:

cd $ANDROID_NDK/sources/cxx-stl/gnu-libstdc++
ln -s 4.4.3/libs
ln -s 4.4.3/include

Apparently version 4.6 (the latest as of this writing) doesn’t work.

At that point, everything should work, but I got an error like this:

Copy bin/android/obj/libApplicationMain.so to bin/android/bin/libs/armeabi/libApplicationMain.so
cd bin/android/bin
/SDKs//ant/bin/ant debug
sh: /SDKs//ant/bin/ant: No such file or directory
Called from ? line 1
Called from InstallTool.hx line 679
Called from InstallTool.hx line 119
Called from installers/InstallerBase.hx line 229
Called from installers/AndroidInstaller.hx line 56
Called from helpers/AndroidHelper.hx line 53
Called from helpers/ProcessHelper.hx line 125
Called from InstallTool.hx line 152
Called from /usr/lib/haxe/std/neko/Lib.hx line 63
Called from helpers/ProcessHelper.hx line 119
Called from helpers/ProcessHelper.hx line 169
Uncaught exception - Error running: /SDKs//ant/bin/ant debug [bin/android/bin]

To fix that, I edited ~/.hxcpp_config.xml to set the various paths:

<section id="vars">
<set name="SDK_ROOT" value="/SDKs/" />
<set name="ANDROID_SDK" value="/opt/android-sdk" />
<set name="ANDROID_SETUP" value="true" />
<set name="ANDROID_NDK_ROOT" value="/opt/android-ndk/" />
<set name="ANT_HOME" value="/usr/share/apache-ant" />
<set name="JAVA_HOME" value="/usr/lib/jvm/java-7-openjdk" />
</section>

I have not done more yet to figure out why I needed to do that.

Note also that you need to include the following NDLLs in your .nmml to compile for Android, though they don’t seem to be needed for other platforms:

<ndll name="std" />
<ndll name="regexp" />
<ndll name="zlib" />
<ndll name="nme" haxelib="nme" />

The latter seems to be needed even if including the nme haxelib. Again, I have not investigated farther.

The Android target also does not like the portrait="*" option in the nmml file, you must specify landscape or portrait.

At this point, you should be able to build and run Android apps, e.g.:

/usr/lib/haxe/lib/nme/3,4,4/samples/02-Text/
nme test Sample.nmml android

Note that the above will only work if you can write to the samples dir, e.g., chown -R joe /usr/lib/haxe/lib/nme/3,4,4/samples/.