Skip to content

Android Build#6992

Draft
Shivansps wants to merge 75 commits into
scp-fs2open:masterfrom
Shivansps:android-build
Draft

Android Build#6992
Shivansps wants to merge 75 commits into
scp-fs2open:masterfrom
Shivansps:android-build

Conversation

@Shivansps
Copy link
Copy Markdown
Contributor

@Shivansps Shivansps commented Aug 23, 2025

Summary: Current Status
-Waiting on SDL3 to be merged

Android OS:

  • Currently working on all archs with 16KB alignment too
  • Running on GLES 3.2 (minimum req, uses functions from it).
  • Limited FFmpeg lib to 6.1 as current master does not work for playing sound on cutscenes. Yet this version seems to work OK.

Note: It is now possible to compile with just an script on a linux x64 system with only having the same dependencies needed to compile normally.

https://github.com/Shivansps/Fso-Android-Prebuilts/blob/main/build_fso_android.sh

==============================================================================
OLD INFO BELOW, for reference only


Libs prebuilts upload and the script to compile both the prebuilt libs and FSO for android on all ABIs are uploaded in this repo: https://github.com/Shivansps/Fso-Android-Prebuilts

I created this PR to document the effort and get some feedback and ideas. Since next week will be unable to expend too much time on it for a few days or weeks.

The idea is to compile FSO as a lib, then have a wrapper android studio project with SDL to pick it up and start it.

So where it this?

  1. I had to make some ugly changes to the cmake build scripts because, probably due to the cross compiling enviroment, the prebuilt libs where not detected. I also saw a bug where FSO_PREBUILT_OVERRIDE was not working and still downloaded the libs anyway because i belive it checks if the prebuilt folder exist on target, and it will not. So i had to workaround all those issues the best i could.

  2. I changed SDL to request OpenGL ES 3.2 in Android, the only real way is to make it run on ES 3.2. I discarted any other workaround.
    I added a cmake flag to enable OpenGL ES mode "FSO_BUILD_WITH_OPENGL_ES" this adds the "USE_OPENGL_ES" definition in code, since OpenGL ES can be used on Linux and Windows too i think that will make the effort to try to make it work easier than dealing with android.
    I think ES should work out of the box on Linux, on Windows the easier way to get ES working is with Mesa/Zink, this not the best thing but if it dosent work there it will not anywhere.
    To get Mesa OpenGL ES working on windows you need to:

Download a prebuilt version https://github.com/pal1000/mesa-dist-win/releases/tag/25.2.0
get mesa3d-25.2.0-release-msvc.7z
Extract and copy form the x64 folder, libEGL.dll, libgallium_wgl.dll and libGLESv2.dll to the exe/output directory

As for the extend of funcionality of the GLES mode, i think its ok to forget about geo shaders and post-processing, and even deferred light and go for the bare minimum needed.
Lacking wireframe mode im not sure what will affect.

3) Current Status: Working directly on Android, with wrapper and external shaders the external shaders are on point 6. With a few issues. Like deffered being broken and my version of the shaders in general being only partially working, if that.

Android wrapper test release here: https://github.com/Shivansps/Fso_Android_Wrapper/releases/

Video: https://www.youtube.com/watch?v=sVqxEbKyS0c

As for the texture compression, that will be an issue, even with Vulkan, the formats supported in desktop and mobile are just... different and may need to implement KTX->ETC2, but thats way out of scope of what im trying to do. Currently, i do belive S3TC and BC7 will be software decompressed to GL_BGRA if there is no hardware support.

The IMGUI status is, it works on Android OK, it can work on Linux under GL ES too, (needs libgles2-mesa-dev for build). On Windows it dosent work under GLES, in fact it crashes if you try to use it and it will crash again when the exit the game.
I think it can be fixed by adding mesa gles lib somehow and forcing imgui into gles mode on windows as well. But i think it is too much trouble for something no one will use.

  1. Filesystem access: a cmdline argument as been added (-working_folder), to set the working folder for FSO, on Android. This cmdline argument is a direct reeplacement to being able to set the working folder for the executable in other OS.
    If no cmdline argument is given, as a fallback, FSO gets the working folder from SDL what will likely be:
    "[phone][internal storage]\Android\data\com.{org}.{app}\files"

  2. Changes to the renderer and shader code: Switched to external shaders, the runtime process will add the precision quantification and expand shaders.
    Im attaching the current version of the shaders:

  3. How to read the fs2_log: log is being saved to the application private storage the only way to read it is with adb.

cd C:\Users[user]\AppData\Local\Android\Sdk\platform-tools
adb shell run-as com.shivansps.fsowrapper cat /data/data/com.shivansps.fsowrapper/files/data/fs2_open.log

  1. How to compile:
    Build system: Linux x64 Debian
    Android NDK R27d: https://developer.android.com/ndk/downloads
    unzip in a folder for easy access

You will need to generate the embeddedfile before anything you will need it for crosscompile, so can generate it by compiling the FSO tools to try this one, it may not work.
embed.zip

I already compiled all dependencies need for the prebuilt directory, you can grab them from here:
prebuilts for android arm64-v8a
https://drive.google.com/file/d/1b2vJKFMfZhcspnSL-7ywq1LT2OHApuzZ/view?usp=sharing
Extract it to a easy access directory, next step ill put the steps to compile the dependendies with the NDK
Note: Used FFmppeg 5.0 as current master fail to init the audio decoder

prebuilts for android x86_x64
https://drive.google.com/file/d/1IpgGBGb9CQ4TIQZFGjqBCSUheu9iTIMI/view?usp=sharing

Build Command:

cmake .. -DFSO_BUILD_WITH_OPENGL_DEBUG=ON -DCMAKE_BUILD_TYPE=Debug -DCMAKE_TOOLCHAIN_FILE=/home/shivan/android-ndk-r27d/build/cmake/android.toolchain.cmake -DANDROID_ABI=arm64-v8a -DANDROID_PLATFORM=android-31 -DEMBEDFILE_PATH=/home/shivan/embed -DFSO_PREBUILT_OVERRIDE=/home/shivan/prebuilt -G Ninja && sed -i 's/-lusb-1.0//' build.ninja

as you can see you need to pass the NDK path, the embeded file path and the prebuilt directory path.
The sed command at the end is to remove "-lusb-1.0" from the linker, that lib is missing from the toolchain and linker does not needed it.

That should give you a "libfs2_open_24_3_0_arm64-DEBUG.so" as result

  1. Android Wrapper:
    A wrapper android app is used to pack the fso bin and the dependencies and then start it passing cmdline arguments and working folder path.
    Copy "libavcodec.so, libavformat.so, libavutil.so, libfs2_open_24_3_0_arm64-DEBUG.so, libopenal.so, libSDL2.so, libswresample.so, libswscale.so" to "FSOWrapper\app\src\main\jniLibs\arm64-v8a" compile and run, if you are going to run in a emulator, remember to create a arm64-v8a one, ive been running it directly on my phone.
    The wrapper repo can be found here, feel free to fork and/or to use as will:
    https://github.com/Shivansps/Fso_Android_Wrapper

Reemplacing nativelibs (.so) files in runtime on Android to provide engine updates without reinstalling/updating the wrapper while its possible, it is a bit complicated to handle and may be misundertood as malicious activity, so with that in mind, in Android i belive engine builds should come already packed with a wrapper in a apk form with minimal functionality, rather than distributing the .so files alone. Then knossos or any other launcher can call the wrapper main activity (or game activity) to launch the game passing arguments and any data as needed.

For x86_64 android and chrome os, it is possible to support too, just everything need to be compiled again with the x86_64 libs and also include them in the jnilibs folder, as it is possible to have both build archs in the apk and android/chrome will use the best one.

  1. Manually compiling dependencies:
    FFmpeg
    Use v5.0 as it is confirmed working, current master fails to decode audio.
    Repo: https://github.com/Javernaut/ffmpeg-android-maker?tab=readme-ov-file

export ANDROID_SDK_HOME=/home/shivan/AndroidSDK
export ANDROID_NDK_HOME=/home/shivan/android-ndk-r27d
./ffmpeg-android-maker.sh --source-git-tag=n5.0

Freetype
Repo: https://github.com/cdave1/freetype2-android

Change ABI and platform on Android/Application.mk
APP_ABI := arm64-v8a
APP_PLATFORM := android-21
export PATH=$PATH:/home/shivan/android-ndk-r27d
./ndk-build

OpenAL Soft
Repo: https://github.com/kcat/openal-soft
Note: OpenAL soft will need to be compiled with the oboe backend.
https://github.com/google/oboe

cmake -DCMAKE_SYSTEM_NAME=Android -DANDROID_NDK=/home/shivan/android-ndk-r27d -DCMAKE_ANDROID_ARCH_ABI=arm64-v8a -DANDROID_PLATFORM=android-31 -DCMAKE_INSTALL_PREFIX="/home/shivan/libopenal" -DALSOFT_REQUIRE_OBOE=ON -DOBOE_SOURCE=/home/shivan/oboe -DALSOFT_REQUIRE_OPENSL=OFF ..
make install

SDL2
Repo: https://github.com/libsdl-org/SDL/tree/SDL2

cmake .. -DCMAKE_TOOLCHAIN_FILE="/home/shivan/android-ndk-r27d/build/cmake/android.toolchain.cmake" -DANDROID_ABI="arm64-v8a" -DANDROID_PLATFORM=android-31 -DCMAKE_BUILD_TYPE=Release -DSDL_STATIC=OFF -DSDL_SHARED=ON -DSDL_TEST=OFF -DSDL_AUDIO=ON -DSDL_VIDEO=ON -DSDL_RENDER=ON -DCMAKE_INSTALL_PREFIX="/home/shivan/libsdl2"
make install

@notimaginative
Copy link
Copy Markdown
Contributor

Regarding point 1, the prebuilt override bug, that's fixed in the SDL3 branch. I keep forgetting to split that off into it's own thing and PR it.

Another thing is that since we've moved to a newer cmake version we can technically replicate embedfile with a platform agnostic cmake script. That's been on my todo list for a while since it's the only thing holding up Windows arm64 builds.

@wookieejedi wookieejedi added the build An issue related to the build systems label Aug 24, 2025
@Shivansps Shivansps force-pushed the android-build branch 2 times, most recently from 2b6fca8 to ca6b8a7 Compare September 23, 2025 22:55
@BMagnu BMagnu added the Waiting for Stable Marks a pull request that is to be merged after the next stable release, due to a release cycle label May 31, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

build An issue related to the build systems Waiting for Stable Marks a pull request that is to be merged after the next stable release, due to a release cycle

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants