Emulator(Native Android)

The Uzebox now have a fully functional emulator! Download and discuss it here.
Post Reply
User avatar
D3thAdd3r
Posts: 3221
Joined: Wed Apr 29, 2009 10:00 am
Location: Minneapolis, United States

Emulator(Native Android)

Post by D3thAdd3r »

Does anyone know what it would take to port CUzebox or Uzem to a native Android application? For me, the Emscripten version does not run full speed on my phone with the default browser. Even if it does run full speed in a better browser in the future, it still seems rather inefficient for a battery powered device. If someone does have a good grasp of how much it would take, would it then be worth it to maintain the extra code is the question.

I find input on cell phones to be the worst problem. You really cannot play NES,SNES,etc emulators well at all due to touch screen just not comparing to buttons. At least then I think there has to be support for Bluetooth input devices. Anyway mostly a curiosity, but it would be neat someday to see an emulator packaged with all the latest roms(auto-updating even) on the Play Store. I guess the same could be said for iOS, but I have even less of any idea about any of that.
User avatar
Artcfox
Posts: 1382
Joined: Thu Jun 04, 2015 5:35 pm
Contact:

Re: Emulator(Native Android)

Post by Artcfox »

The Android port is currently working and there is a beta version available for download later in this thread:

Link to latest beta version, along with details about the different touch zones. Tilt for D-pad.

If you have a USB On-The-Go adapter, you can also plug a keyboard directly into your Android device and it will work the same as it does on a computer. Game controllers are not supported yet.


Edit: My old post (for posterity's sake is below)
Apparently SDL2 works on Android, and you can compile C++ code on Android, but I've never made an Android application before. I've thought about what it would take to do that, and it might just be a matter of finding an example C++ SDL2 Android app, and swapping the guts out for uzem or cuzebox.

On the subject of controls, I received my USB XBox360 controller and tried it with Uzem, but I still need to figure out how to remap the buttons to be correct. It works, and I can play games, but the buttons are mapped weirdly. Supposedly if I run a user-mode driver in Linux, I can configure the controller to map to keypresses, but I haven't done that yet because work has been super busy lately, and I'm providing the entertainment for two out of state coworkers after work.

I think it's possible to plug a USB gamepad into an Android device just with a USB OTG cable. I know that works for a keyboard and mouse.
Last edited by Artcfox on Wed Sep 27, 2017 1:58 pm, edited 2 times in total.
User avatar
Jubatian
Posts: 1561
Joined: Thu Oct 01, 2015 9:44 pm
Location: Hungary
Contact:

Re: Emulator(Native Android)

Post by Jubatian »

I am thinking about creating a LibRetro core from CUzeBox (or to support it as target), this will be done a little later, but I feel it quite possible as even SDL itself is rather separated from the innards. LibRetro should then solve this problem by having Android support, possibly along with many other things which otherwise would have to be implemented directly.
User avatar
D3thAdd3r
Posts: 3221
Joined: Wed Apr 29, 2009 10:00 am
Location: Minneapolis, United States

Re: Emulator(Native Android)

Post by D3thAdd3r »

@Artcfox I thought I remembered the USB 360 controller working well. In Uzem you should be able to press 7 and follow the console window text to assign directly physical buttons to virtual ones. On OTG cables that is even better, and they are dirt cheap. I swear Bluetooth controllers have noticeable lag feeling.

@Jubatian Huh, that Libretro looks quite good. If for no other benefit than having a real GUI across different platforms that didn't require much maintenance. I might be misunderstanding what Libretro features are with that statement though.
User avatar
Artcfox
Posts: 1382
Joined: Thu Jun 04, 2015 5:35 pm
Contact:

Re: Emulator(Native Android)

Post by Artcfox »

D3thAdd3r wrote:@Artcfox I thought I remembered the USB 360 controller working well. In Uzem you should be able to press 7 and follow the console window text to assign directly physical buttons to virtual ones. On OTG cables that is even better, and they are dirt cheap. I swear Bluetooth controllers have noticeable lag feeling.
OMG! Thank you so much! This even allows me to map the analog stick to act as a D-pad! It's a bit sensitive, but this is really awesome. (I'm still a lot better at playing Bugz using the keyboard, and I've considered making a custom controller that has individual buttons for the D-pad, since it's way too hard to press up or down without also pressing left or right.)
User avatar
D3thAdd3r
Posts: 3221
Joined: Wed Apr 29, 2009 10:00 am
Location: Minneapolis, United States

Re: Emulator(Native Android)

Post by D3thAdd3r »

There could be added to an emulator using SDL, a joystick "dead zone", that would decrease the sensitivity for triggering a direction. Basically it is how far in any direction before it registers, so then each direction becomes more distinct but also requires further travel which feels less responsive to changes. Hardest part about that is implementing code to actually get those preferences from the user in a simple sensible way without a GUI.

Now that you mention it, I am not sure why the hell I play with the keyboard still. These are so cheap and would provide the exact feel that I should pick some up.
User avatar
Artcfox
Posts: 1382
Joined: Thu Jun 04, 2015 5:35 pm
Contact:

Re: Emulator(Native Android)

Post by Artcfox »

Yeah, it looks like the code does something with a deadzone, so maybe that just needs a bit of tweaking.

Wow! Those retro controllers are cheap!
User avatar
Artcfox
Posts: 1382
Joined: Thu Jun 04, 2015 5:35 pm
Contact:

Re: Emulator(Native Android)

Post by Artcfox »

So I've done a bit of research, and found this video:



However it is a bit outdated, since the latest Android IDE is Android Studio, not Eclipse, and new build system it uses is Gradle.

I installed the SDK and from inside the SDK, I installed the NDK.

I basically followed the instructions in the video, but (on Fedora) I had to:

Code: Select all

sudo dnf install SDL2-devel.i686
and when I downloaded SDL2, I had to go inside its include directory and do:

Code: Select all

ln -s SDL_config_android.h SDL_config-arm.h
ndk-build wasn't on my path, but a:

Code: Select all

locate ndk-build
told me where it was, and then I ran it using the full path.

I opened Android.mk in the jni/src directory and edited it to list all of the cuzebox .c files (except for filesmin.c to avoid multiply defined symbols). Additionally in another spot on my filesystem, I configured a native build of cuzebox to use an external gamefile.uze, and then snagged the gamefile.c it generated and copied it over to the jni/src directory, and added it to the list as well.

The full contents of my jni/src/Android.mk file are:

Code: Select all

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_MODULE := main

SDL_PATH := ../SDL

LOCAL_C_INCLUDES := $(LOCAL_PATH)/$(SDL_PATH)/include

# Add your application source files here...
LOCAL_SRC_FILES := $(SDL_PATH)/src/main/android/SDL_android_main.c \
	audio.c \
	avconv.c \
	chars.c \
	conout.c \
	cu_avr.c \
	cu_avrc.c \
	cu_avrfg.c \
	cu_ctr.c \
	cu_hfile.c \
	cu_spi.c \
	cu_spir.c \
	cu_spisd.c \
	cu_ufile.c \
	cu_vfat.c \
	eepdump.c \
	filesys.c \
	frame.c \
	guicore.c \
	main.c \
	textgui.c \
	gamefile.c

LOCAL_SHARED_LIBRARIES := SDL2

LOCAL_LDLIBS := -lGLESv1_CM -lGLESv2 -llog

include $(BUILD_SHARED_LIBRARY)
Eventually it successfully compiled and linked, and gave me a libmain.so and libSDL2.so! :)

However since this was based off an old SDL2 project file w/o Gradle support, that's where I got stuck. :(

Searching for "Android Studio SDL2 NDK" I then found this project which claims to support SDL2 with Gradle, and did the same thing with the source files, removed the broken symlinks to SDL2 and glm, remade the symlink (note, this project expects a different name for the symlink!) to the proper SDL2 folder, and edited the Android.mk file inside the jni/src directory so it didn't use any of the GLM stuff, and so it included the cuzebox sources.

My full jni/src/Android.mk file for the new project looks like:

Code: Select all

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_MODULE := main

SDL_PATH := ../SDL2
#GLM_PATH := ../glm

LOCAL_C_INCLUDES := $(LOCAL_PATH)/$(SDL_PATH)/include

    # $(LOCAL_PATH)/$(GLM_PATH)/ \
    # $(LOCAL_PATH)/$(GLM_PATH)/gtc \
    # $(LOCAL_PATH)/$(GLM_PATH)/gtx \
    # $(LOCAL_PATH)/$(GLM_PATH)/detail \
    # $(LOCAL_PATH)/$(GLM_PATH)/glm.hpp

# Add your application source files here...
LOCAL_SRC_FILES := $(SDL_PATH)/src/main/android/SDL_android_main.c \
	audio.c \
	avconv.c \
	chars.c \
	conout.c \
	cu_avr.c \
	cu_avrc.c \
	cu_avrfg.c \
	cu_ctr.c \
	cu_hfile.c \
	cu_spi.c \
	cu_spir.c \
	cu_spisd.c \
	cu_ufile.c \
	cu_vfat.c \
	eepdump.c \
	filesys.c \
	frame.c \
	guicore.c \
	main.c \
	textgui.c \
	gamefile.c


LOCAL_SHARED_LIBRARIES := SDL2

LOCAL_LDLIBS := -lGLESv1_CM -lEGL -lGLESv3 -llog

include $(BUILD_SHARED_LIBRARY)
running ndk-build by hand made the libraries, and then from within the Android Studio GUI I was able to go to Run... and then it finally created a debug .apk.

When I tried to run this on my phone, it just crashed however, but I'm completely new at Android stuff, so it's possible that I'm missing something easy that would make it all work properly.

If anyone else wants to try getting this to work, it looks like it might not be as much work as one might think, and then we would have a native Android build of Cuzebox!
User avatar
D3thAdd3r
Posts: 3221
Joined: Wed Apr 29, 2009 10:00 am
Location: Minneapolis, United States

Re: Emulator(Native Android)

Post by D3thAdd3r »

Huh, cool very interesting. Promising that you actually got the source to build for Android. I wish I knew anything about all this arcane stuff, it really is important details. Still the end product might be interesting enough for someone to bring it to fruition. How sweet it would be to have the thing auto update where a new game comes out, and you just pull it up on your phone and try it(similar to the level of cool that the emscripten emulator is). I only worry even the native application will not run full speed maybe?
User avatar
Artcfox
Posts: 1382
Joined: Thu Jun 04, 2015 5:35 pm
Contact:

Re: Emulator(Native Android)

Post by Artcfox »

I finally ported CUzeBox to Android!

I did this using a Debian 8 Live CD, so I really hope that I remember all the steps. :lol:

I wrote down some of the important steps:

Code: Select all

sudo dpkg --add-architecture i386
sudo apt-get update
sudo apt-get install lib32stdc++6 lib32z1 libsdl2-dev:i386 libegl1-mesa-dev:i386 libgles2-mesa-dev:i386 libwayland-dev:i386
I downloaded the libsdl2 sources from its homepage, copied the android-project folder from inside it to my home directory, and imported it as an existing project into Android Studio. Then I had to right-click on the build.gradle (Module: app) file and choose "Add External Build File" and I had to pick the src/main/jni/Android.mk file (NOT the src/main/jni/src/Android.mk file!).

The src/main/jni/src/Android.mk (yes, that extra /src/ near the end is very important!) that ended up working was this:

Code: Select all

include $(CLEAR_VARS)

LOCAL_MODULE := main

SDL_PATH := ../SDL

LOCAL_C_INCLUDES := $(LOCAL_PATH)/$(SDL_PATH)/include

LOCAL_CFLAGS := -DFLAG_SELFCONT=1 -DFLAG_NOCONSOLE=1 -DFLAG_DISPLAY_GAMEONLY=1

# Add your application source files here...
LOCAL_SRC_FILES := $(SDL_PATH)/src/main/android/SDL_android_main.c \
	audio.c \
	chars.c \
	conout.c \
	cu_avr.c \
	cu_avrc.c \
	cu_avrfg.c \
	cu_ctr.c \
	cu_hfile.c \
	cu_spi.c \
	cu_spir.c \
	cu_ufile.c \
	eepdump.c \
	filesmin.c \
	frame.c \
	gamefile.c \
	guicore.c \
	main.c \
	textgui.c

LOCAL_SHARED_LIBRARIES := SDL2

LOCAL_LDLIBS := -lGLESv1_CM -lGLESv2 -llog

include $(BUILD_SHARED_LIBRARY)
The default API versions from the libsdl2 sample project (10 and 12) wouldn't let me build successfully (even after installing those older SDKs), so I bumped them up to the lowest SDK version that Android Studio would let me install, which was 17 (Android 4.2.2), and left the target SDK version at 25. It works on my Pixel XL, and hopefully it will work on other people's devices.

If anyone wants to download the entire Android Studio project source code that I used to build these apks (without the code-signing for release builds), click here.

This is literally just the sample application that came with libsdl2, with the .c file replaced with the .c and .h files of CUzeBox. No bells, no whistles, I didn't even change the name of the application, or its icon. This is just a proof of concept. I've never build an Android application before, so I have no idea what I'm doing.

If you want to replace the gamefile, just download and configure cuzebox for a self-contained build in a different place on your hard drive, and then copy over the gamefile.c it generates into the src directory of the android project. I'm sure someone who knows more about Android can make a snazzy GUI for all this, I just wanted to see if I could get it working.

I do think however that it's time that CUzeBox gets proper 2-player "joystick" support, so instead of having to plug a keyboard into your phone or tablet, we can use multiple Bluetooth SNES controllers. ;)

Edit: I figured out how to make a release build, so I swapped the attached file for a release build and it runs smooth as butter at 60fps.
Edit 2: For some performance testing, I displayed the debug output (using F3) and then pressed F4 to turn off the frame limiter, and CUzeBox runs at 230% speed on my Pixel XL. When running at 100%, 60fps it doesn't get warm at all. Awesome job Jubatian! I do like the idea of having a GUI to swap games (use the thumbnails from the wiki page?), and maybe even have a push notification when a new game is released, so you can automatically download and install it.
Edit 3: I swapped the apks for ones that should run on versions of Android all the way down to 4.2.2. When I bumped the minSdkVersion down to 17, then the max it runs with the framerate limiter off is 206% on my Pixel XL, so it would appear that it sacrificed a tiny bit of speed in order to be compatible with almost every single device out there.
Attachments
cuzebox-android-laser2.zip
Android port of CUzeBox w/ Laser Puzzle II pre-loaded. Release Build. Uses minSdkVersion 17, requires keyboard (use a USB OTG adapter, or a Bluetooth keyboard)
(1.69 MiB) Downloaded 700 times
android-cuzebox-bugz.zip
Android port of CUzeBox w/ Bugz pre-loaded. Release Build. Uses minSdkVersion 17, requires keyboard (use a USB OTG adapter, or a Bluetooth keyboard)
(1.67 MiB) Downloaded 707 times
Post Reply