This is part 3 of my HowTo: SDL on Android series.
(prev)
Now let’s get some more native libraries linked into our app. I probably don’t have to tell you how important this is, since you can’t make a whole lot of games or apps without text, sound, or music.
SDL_ttf
Adding a satellite library like SDL_ttf leads us through several steps. These are roughly the same for each library, so I’ll only go over this one in specifics.
1) Download the source. Get the latest source from the Mercurial repository or grab a snapshot from the official page.
2) Place source in project. Put the SDL_ttf source directory alongside your SDL directory in your project (in jni/ so you get jni/SDL_ttf).
3) Gather dependencies. The way everything is set up, you have to be particular about the directory placement and naming. The SDL extension libraries mostly expect their dependency directories to be in jni/ and to be named in their simple form (e.g. libDependency-0.3.0/ would be dependency/). For SDL_ttf, we need to get the FreeType2 library. Go to the FreeType official downloads. You might end up in a list of files to download. The latest version should be good. As of this writing, that is “freetype-2.4.11.tar.gz” (you don’t need the doc or demo archives). Yeah, you’ll probably need a good unzip program that can handle tar.gz or tar.bz2 archives. Now, SDL_ttf strangely expects FreeType to live within the SDL_ttf directory. Copy or move it over into the jni/SDL_ttf directory and rename it to “freetype”.
4) Add include and linker flags for the library. Open up your jni/src/Android.mk file. Add $(LOCAL_PATH)/../SDL_ttf to the LOCAL_C_INCLUDES line. That will give all of our files access to the SDL_ttf.h header. SDL_ttf knows how to build itself (it has an Android.mk), so it will create a shared library that we can link to. Add SDL2_ttf (note the “2”) to the LOCAL_SHARED_LIBRARIES line. The library is linked as SDL2_ttf so you can install it alongside SDL_ttf built for SDL1.2 as necessary.
5) Tell SDL to load the library at runtime. The last thing is to get the C library loaded from the Java code that really drives the app. Open up src/org/libsdl/app/SDLActivity.java. In the SDLActivity class, there’s a static block (line 58 in my copy) that loads the .so files. Uncomment or add the line:
System.loadLibrary("SDL2_ttf");
Now when ndk-build runs, it should pull in SDL_ttf and pump out the .so. Then when the .apk is installed and run, the Java code will load the C library for you. Now you can work with the library just as usual.
If you have anything to add, please let me know in the comments!
Thanks you’re an angel.
I just used this tutorial to port SDL_image. It was the same way as SDL_ttf but I just had to comment these lines because I haven’t got the dependencies I guess:
SUPPORT_WEBP := true
WEBP_LIBRARY_PATH := external/libwebp-0.3.0
Hay! Can you help ? What did you change in you jni/src/Android.mk file, as I am getting an error like this :
make: *** No rule to make target `/media/Work/Workpsace/Codespace/Engine_Workspace/android/android-project/jni/src/../SDL_image/src/main/android/SDL_android_main.c’, needed by `/media/Work/Workpsace/Codespace/Engine_Workspace/android/android-project/obj/local/armeabi/objs/main/__/SDL_image/src/main/android/SDL_android_main.o’. Stop.
That error says, in a roundabout way, that it couldn’t find the file you want to compile. That it says “SDL_image” is fishy to me. Double-check the path you put in (and any macro expansions therein), because it should probably render as “SDL” instead.
If you copy the webp folder to the jni folder, it works.
Same issue with SDL2_mixer and its dependencies SMPEG and libmikmod.
This happends because the libs required were not already built when SDL2_image and SDL2_mixer were about to be linked… don’t know why really.
Hope it helps… it annoyned me for a while
How do you execute TTF_OpenFont() ? Normally it would require that you pass a path in like text_font = TTF_OpenFont(“../../fonts/FreeSans.ttf”, 24); but you can’t just simply do this in ndk… I looked up how to access files on the droid filesystem and it’s messy as hell..
As long as you can specify the path correctly (the tough part), you can use normal C filesystem calls. To make it easier, SDL’s RWops system on Android looks in the APK’s assets/ directory first. So put your assets (fonts, etc.) in that directory, package up the APK, then it can read them from there. The usual loading functions that SDL and its satellite libs (and SDL_gpu) use go through RWops, so they all automatically check there.