Building SDL 2.0.12 with Android Studio 4.0 on Mac OS Catalina

This is the updated tutorial to set up and build an app with SDL2.0.12 in Android Studio 4.0 in Mac OS Catalina

For this instructions we wish to create a app named DemolitionCrew. Change accordingly to your situation.
Since all the examples is from a real game I have released on iOS, Android and Switch I will use its name.

We need to utilize not only the SDL2 main lib but also SDL2_Image, SDL2_net etc
I will compile and run this on a Samsung Tablet (SM-T585)

NOTE:

During the build process you might need to click on “Sync with gradle”
Also you will need to klick on install SDK somewhere in the bottom.
Accept the license agreement.

Mac OS can complain that some tools like make and clang is not from a trusted developer.
When this pops upp:
Then click on “cancel” on the popup window.
Open Settings -> Security and integrity-> General settings tab.
Click on the lock in the bottom left.
As you see it mentions “make”.
Click on “allow anyway”

To make this permanent.
Open a terminal and write
sudo spctl --master-disable
To be able to select the third option “from anywhere”

The next time this pops up you can now choose open.
This will also happen for “python”, “clang”, “clang++”, “ld”, “x86_64-linux-android-ar”, “LLVMgold.dylib”, “i686-linux-android-ar”
After each complain you will need to click “Build -> Make project” again.
The exception you make for each tool only lasts for one hour so you might have to do this several times the first
time you build att the SDL components.

1. Create this folder structure

Folder Structure
~ means the users home directory

~/development/android
~/development/android\sdl2
~/development/android\sdl2_image
~/development/android\sdl2_mixer
~/development/android\sdl2_net
~/development/android\sdl2_ttf

2. Download these zip archives with source:
https://www.libsdl.org/download-2.0.php
https://www.libsdl.org/projects/SDL_image/
https://www.libsdl.org/projects/SDL_mixer/
https://www.libsdl.org/projects/SDL_net/
https://www.libsdl.org/projects/SDL_ttf

3. unpack every zip to individual folders

4. Copy the content to correct folders
From the SDL2.0.10 folder you copy the folder “android-project” to ~/development/android
From the SDL2.0.10 folder you copy “include”,“src” and “Android.mk” to ~/development/android/SDL2
From the “SDL2_image-2.0.5” folder you copy all files ending with .c and .h and the folder “external” and the file Android.mk to ~/development/android/SDL2_image
From the “SDL2_ttf-2.0.15” folder you copy all files ending with .c and .h and the folder “external” and the file Android.mk to ~/development/android/SDL2_ttf
From the “SDL2_net-2.0.1” folder you copy all files ending with .c and .h and the file Android.mk to ~/development/android/SDL2_net
From the “SDL2_mixer-2.0.4” folder you copy all files ending with .c and .h and the folders “external”,“native_midi”,“timidity” and the file Androis.mk to ~/development/android/SDL2_mixer

6. Create the Project.
In the folder “~/development/android”
Rename the folder “android-project” to what you want your project to be called.
In this case we name it “DemolitionCrew”

7. Start the terminal

Create these links so they will appear as linked folders in the project. It is important that
you have named your project folder in beforehand. Otherwise they disappear.

ln -s ~/development/android/sdl2 ~/development/android/DemolitionCrew/app/jni/SDL
ln -s ~/development/android/sdl2_image ~/development/android/DemolitionCrew/app/jni/SDL_image
ln -s ~/development/android/sdl2_mixer ~/development/android/DemolitionCrew/app/jni/SDL_mixer
ln -s ~/development/android/sdl2_net ~/development/android/DemolitionCrew/app/jni/SDL_net
ln -s ~/development/android/sdl2_ttf ~/development/android/DemolitionCrew/app/jni/SDL_ttf

8. Download Android Studio 4.0
Download Android Studio 4.0 from https://developer.android.com/studio
Install
During the installation MacOS complains over some components that are not compatible with future MacOS versions.

Start Android studio

Click on “Open an existing Android Studio Project”
Navigate to “~/development/android” and select your project. In this case “DemolitionCrew”.
Click “Open”

9. Change view
In the almost top left corner you can alter the view between “Android” and “Project”
Change to “Project” if it is not already choosen.

Expand the tree view DemolitionCrew->app->src->main

Double Click on AndroidManifest.xml

Change the package=“org.libsdl.app” on line 6 to package=“com.xirbx.games” (Or what your company and app name is)

The android:versionCode=“1” Not sure if this needs to be increased for each release on the google play store, but increase it anyways.
Change this to required true if you want touch screen to work on all smart phones.

<uses-feature
android:name="android.hardware.touchscreen"
android:required="true" />

Add these lines under the other permission lines if you wish SDL_net to access your local net and the internet

<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

Save the file (command+S)

10. Expand the tre view to this:
DemolitionCrew->app->jni
Double click on “Application.mk

Uncomment line 5 so that it says
APP_STL := c++_shared

Make sure line 10 says:
APP_PLATFORM=android-16
Add a line underneath that says
APP_CPPFLAGS += -fexceptions

Expand the tree to DemolitionCrew->app
Double click on build.gradle
Make sure line 16 says :

minSdkVersion 16

Make sure line 22 says:

arguments “APP_PLATFORM=android-16”

Change the ApplicationId on line 14 to this:

applicationId “com.xirbx.games.demolitioncrew”

NOTE! On line 18 you need to increase the versionCode for each build you
upload to Google Play

11. Expand the tre view to this:
DemolitionCrew->app->jni->src
Double click on “Android.mk

Change line 14 from

LOCAL_SHARED_LIBRARIES := SDL2

to:

LOCAL_SHARED_LIBRARIES := SDL2 \
SDL2_image \
SDL2_mixer \
SDL2_ttf \
SDL2_net

Change line 12 from:

LOCAL_SRC_FILES := YourSourceHere.c

to

LOCAL_SRC_FILES := \
			AssetManager.cpp \
			Components.cpp \
			ECS.cpp \
			Game.cpp \
			GameClient.cpp \
			GameMap.cpp \
			main.cpp \
			TextureManager.cpp \
			tinyxml2.cpp \
			UrlReader.cpp \
			Vector2D.cpp \
			xmltest.cpp \
			ResourcePath.cpp \
			tmxparser/base64/base64.cpp \
			tmxparser/miniz.c \
			tmxparser/TmxColor.cpp \
			tmxparser/TmxEllipse.cpp \
			tmxparser/TmxGroupLayer.cpp \
			tmxparser/TmxImage.cpp \
			tmxparser/TmxImageLayer.cpp \
			tmxparser/TmxLayer.cpp \
			tmxparser/TmxMap.cpp \
			tmxparser/TmxObject.cpp \
			tmxparser/TmxObjectGroup.cpp \
			tmxparser/TmxPolygon.cpp \
			tmxparser/TmxPolyline.cpp \
			tmxparser/TmxProperty.cpp \
			tmxparser/TmxPropertySet.cpp \
			tmxparser/TmxTerrain.cpp \
			tmxparser/TmxTerrainArray.cpp \
			tmxparser/TmxText.cpp \
			tmxparser/TmxTile.cpp \
			tmxparser/TmxTileLayer.cpp \
			tmxparser/TmxTileOffset.cpp \
			tmxparser/TmxTileset.cpp \
  			tmxparser/TmxUtil.cpp 

NOTE! You only have to list your .cpp and .c files. It will get the header-files
automatically.

Save the file (command + S)

12. Expand DemolitionCrew->app->src->main
Here you will see “java”, “res” and “AndroidManifest.xml
NOTE! It is easy to accidentally choose the wrong src-folder.

Right click on “DemolitionCrew->app->src->main”
Select New->Folder->Assets Folder. (NOT Directory. the folder option is the one with a android figure on)
A window pops up. Click “Finish”
A new folder is created called “assets”

13. It is OK to breath now! :slight_smile:
Now you can minimize the Android studio window and in finder
open up our project folder:
In this folder i place all my assets:
~/development/android/DemolitionCrew/app/src/main/assets
Assets are stuff like all your game graphics, sound, music and levels.

In this folder i place all my C++ and C code
~/development/android/DemolitionCrew/app/jni/src
Also place all the header files for SDL including SDL_mixer.h, SDL_image.h, SDL_ttf.h and SDL_net.h
I guess there is a better way to do this but I was desperate. :slight_smile:

14. Go back to Android Studio
Navigate to DemolitionCrew->app->jni->src in the tree view
If you have a a main.cpp file, it can look something like this.

#include “main.h”
extern “C”
{
using namespace std;
Game *game=nullptr;

int SDL_main(int argc, char* argv[])
{

game = new Game();
game->gameState=gs_LOADING_GAME;
game->init(“Game”); // Setting up SDL stuff and open screens

while(game->running())
{
game->update();
game->render();

}
game->clean();

return 0;

}

}

The important stuff here is the extern “C” after the #includes but before everything else
and that you should use SDL_main() instead of plain main()

15. It is time to make a java-class for our game.
Navigate to DemolitionCrew->app->src->main->java
Right click “java” and select “New->Package”. Name it “com.xirbx.games”
Right click “com.xirbx.games” and select “New->File”. Name it “DemolitionCrew.java” (Or your game name)

Double click on DemolitionCrew.java
and paste this text:

package com.xirbx.games;

import org.libsdl.app.SDLActivity;

/**
A sample wrapper class that just calls SDLActivity
*/

public class DemolitionCrew extends SDLActivity { }

16. Expand the tree view DemolitionCrew->app->src->main

Double Click on AndroidManifest.xml

On line 72 , change from:

<activity android:name="SDLActivity"

To:

<activity android:name="DemolitionCrew"

Save file (command + S)

17. Naming the Game Icon

Expand the tree to this:
DemolitionCrew->app->src->main->res->values
Double click on the “strings.xml”
Change:

<string name="app_name">Game</string>

To:

<string name="app_name">Demolition Crew</string>

This string is where the AndroidManifest.xml gets its game name value from.
I guess you can localize this for different languages.

18. Changing the Icon picture
Expand the tree to this:
DemolitionCrew->app->src->main->res
In each folder that begins with “mipmap” there is a png image called “ic_launcher.png”
Replace those with your own images.
Make sure they are the correct sizes.

I think it is easier to change those from finder and not in Android studio.

19. When all this is done you should be able to build the entire project. (command+F9)

20. Connect a Android device (That is set to developer mode I guess) and press Run (SHIFT +F10)

I hope this tutorial saved you some time. Please check out my games on App store, Google Play
and Nintendo eShop!
Buy it and spread the word (preferable the Switch version) so I can make some money. :slight_smile:
Jesper / xirBX AB

1 Like

Thank you very much sir. You are amazing!

1 Like

Do I need to copy all the header files in sdl2_net, sdl2, sdl2_image, sdl2_ttf , sdl2_mixer to the jni/src/ folder?

Only SDL_image.h, SDL_net.h, SDL_ttf.h and SDL_mixer.h from those folders
and then all the files from the SDL2/include folder.

This works but is not the prettiest solution. The best thing is to point to include original folders
in the include path. I will do this in the next tutorials I do.

Please give a example c++ program to test run.

Point 14 in this tutorial gives an example of the main.cpp
There is a lot of actual working SDL-code in this forum and everywhere on the internet.
This tutorial is more about how to get your exsisting c++/SDL code to compile in Android Studio.
In the future/near future I will have tutorials how to develop simple games but right now I dont’t have time for that.

Oh, sorry. I didn’t see it. I will check the forums. Thanks

1 Like

I have found a solution to accept the components that are not signed permanent.

Open a terminal and write:
sudo spctl --master-disable

Now you can choose the third option that is “from anywhere”

Thank you! I was wondering how I could achieve the same thing but actually with prebuilt libraries of SDL2.
I tried by making specific module for hidapi, SDL2 and SDL2_main

# Example with SDL2
# Same for hidapi (SHARED) and SDL2_main (STATIC)

LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := SDL2
LOCAL_SRC_FILES := $(SDL2_ANDROID_PATH)/$(TARGET_ARCH_ABI)/lib/libSDL2.so
LOCAL_EXPORT_C_INCLUDES := $(SDL2_ANDROID_PATH)/$(TARGET_ARCH_ABI)/include
include $(PREBUILT_SHARED_LIBRARY)

then for my project here’s the makefile

include $(CLEAR_VARS)
LOCAL_MODULE := main
LOCAL_SRC_FILES :=  $(wildcard $(PROJECT_SRC_PATH)/*.cpp)
LOCAL_SHARED_LIBRARIES := SDL2
LOCAL_LDLIBS := -lvulkan
ifeq ($(NDK_DEBUG),1)
    cmd-strip :=
endif
include $(BUILD_SHARED_LIBRARY)

Unfortunately, the android app crashes saying that hidapi lib is not found. I also tried to add hidapi module into LOCAL_SHARED_LIBRARIES variable of the main module, but it doesn’t change anything…

Any idea?

Make sure to tell the compiler to use c++_shared.

In my example under point 10 you must uncomment the line:
APP_STL := c++_shared
in the file DemolitionCrew->app->jni->Application.mk
That could be the reason.