Making an android module always crash

:information_source: Attention Topic was automatically imported from the old Question2Answer platform.
:bust_in_silhouette: Asked By leo_lau_racefit

I am new to Godot and I am following the tutorial to add custom function on Android.
https://docs.godotengine.org/en/3.1/development/cpp/creating_android_modules.html

After I add custom code (same as the tutorial), the app crash with the following error.

--------- beginning of crash
2020-02-25 10:54:44.774 927-927/org.godotengine.character E/AndroidRuntime: FATAL EXCEPTION: main
	Process: org.godotengine.character, PID: 927
	java.lang.RuntimeException: Unable to instantiate activity ComponentInfo{org.godotengine.character/com.godot.game.GodotApp}: java.lang.InstantiationException: java.lang.Class<com.godot.game.GodotApp> has no zero argument constructor
		at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3340)
		at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3594)
		at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:83)
		at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
		at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
		at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2146)
		at android.os.Handler.dispatchMessage(Handler.java:107)
		at android.os.Looper.loop(Looper.java:237)
		at android.app.ActivityThread.main(ActivityThread.java:7762)
		at java.lang.reflect.Method.invoke(Native Method)
		at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:493)
		at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1047)
	 Caused by: java.lang.InstantiationException: java.lang.Class<com.godot.game.GodotApp> has no zero argument constructor
		at java.lang.Class.newInstance(Native Method)
		at android.app.AppComponentFactory.instantiateActivity(AppComponentFactory.java:95)
		at android.support.v4.app.CoreComponentFactory.instantiateActivity(CoreComponentFactory.java:43)
		at android.app.Instrumentation.newActivity(Instrumentation.java:1251)
		at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3328)
		at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3594) 
		at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:83) 
		at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135) 
		at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95) 
		at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2146) 
		at android.os.Handler.dispatchMessage(Handler.java:107) 
		at android.os.Looper.loop(Looper.java:237) 
		at android.app.ActivityThread.main(ActivityThread.java:7762) 
		at java.lang.reflect.Method.invoke(Native Method) 
		at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:493) 
		at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1047) 
		

This is the code I added (copy and paste A singleton object template):

public class GodotApp extends Godot.SingletonBase {

	protected Activity appActivity;
	protected Context appContext;
	private int instanceId = 0;

	public int myFunction(String p_str) {
		// a function to bind
		return 1;
	}

	public void getInstanceId(int pInstanceId) {
		// You will need to call this method from Godot and pass in the get_instance_id().
		instanceId = pInstanceId;
	}

	static public Godot.SingletonBase initialize(Activity p_activity) {
		return new GodotApp(p_activity);
	}

	public GodotApp(Activity p_activity) {
		//register class name and functions to bind
		registerClass("MySingleton", new String[]
				{
						"myFunction",
						"getInstanceId"
				});
		this.appActivity = p_activity;
		this.appContext = appActivity.getApplicationContext();
		// you might want to try initializing your singleton here, but android
		// threads are weird and this runs in another thread, so to interact with Godot you usually have to do
		appActivity.runOnUiThread(new Runnable() {
			public void run() {
				//useful way to get config info from project.godot
				String key = GodotLib.getGlobal("plugin/api_key");
				//SDK.initializeHere();
			}
		});

	}

	// forwarded callbacks you can reimplement, as SDKs often need them

	protected void onMainActivityResult(int requestCode, int resultCode, Intent data) {}
	protected void onMainRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {}

	protected void onMainPause() {}
	protected void onMainResume() {}
	protected void onMainDestroy() {}

	protected void onGLDrawFrame(GL10 gl) {}
	protected void onGLSurfaceChanged(GL10 gl, int width, int height) {} // singletons will always miss first onGLSurfaceChanged call

}

Before I add any code on Java file, it runs no problem.
It can also run on PC smoothly.
My configuration:

  • Android: Android Studio 3.5.3
  • NDK(side by side): 21.0.6113669
  • Java: jdk-12.0.2
  • Phone: Samsung Galaxy S10 with Android 10.
  • The app is run by connecting my phone via USB cable and pressing Android icon on the top-right corner.

Thank you for your patient.