Browse Source

Specify the path to the Java SDK used for the Android gradle build

Introduce an editor setting to allow users the ability to specify the path to the Java SDK used for the Android gradle build.
Fredia Huya-Kouadio 1 year ago
parent
commit
85e98ef009

+ 2 - 0
platform/android/export/export.cpp

@@ -42,6 +42,8 @@ void register_android_exporter_types() {
 
 
 void register_android_exporter() {
 void register_android_exporter() {
 #ifndef ANDROID_ENABLED
 #ifndef ANDROID_ENABLED
+	EDITOR_DEF("export/android/java_sdk_path", OS::get_singleton()->get_environment("JAVA_HOME"));
+	EditorSettings::get_singleton()->add_property_hint(PropertyInfo(Variant::STRING, "export/android/java_sdk_path", PROPERTY_HINT_GLOBAL_DIR));
 	EDITOR_DEF("export/android/android_sdk_path", OS::get_singleton()->get_environment("ANDROID_HOME"));
 	EDITOR_DEF("export/android/android_sdk_path", OS::get_singleton()->get_environment("ANDROID_HOME"));
 	EditorSettings::get_singleton()->add_property_hint(PropertyInfo(Variant::STRING, "export/android/android_sdk_path", PROPERTY_HINT_GLOBAL_DIR));
 	EditorSettings::get_singleton()->add_property_hint(PropertyInfo(Variant::STRING, "export/android/android_sdk_path", PROPERTY_HINT_GLOBAL_DIR));
 	EDITOR_DEF("export/android/debug_keystore", "");
 	EDITOR_DEF("export/android/debug_keystore", "");

+ 50 - 4
platform/android/export/export_plugin.cpp

@@ -2111,8 +2111,17 @@ Ref<Texture2D> EditorExportPlatformAndroid::get_run_icon() const {
 	return run_icon;
 	return run_icon;
 }
 }
 
 
+String EditorExportPlatformAndroid::get_java_path() {
+	String exe_ext;
+	if (OS::get_singleton()->get_name() == "Windows") {
+		exe_ext = ".exe";
+	}
+	String java_sdk_path = EDITOR_GET("export/android/java_sdk_path");
+	return java_sdk_path.path_join("bin/java" + exe_ext);
+}
+
 String EditorExportPlatformAndroid::get_adb_path() {
 String EditorExportPlatformAndroid::get_adb_path() {
-	String exe_ext = "";
+	String exe_ext;
 	if (OS::get_singleton()->get_name() == "Windows") {
 	if (OS::get_singleton()->get_name() == "Windows") {
 		exe_ext = ".exe";
 		exe_ext = ".exe";
 	}
 	}
@@ -2124,13 +2133,13 @@ String EditorExportPlatformAndroid::get_apksigner_path(int p_target_sdk, bool p_
 	if (p_target_sdk == -1) {
 	if (p_target_sdk == -1) {
 		p_target_sdk = DEFAULT_TARGET_SDK_VERSION;
 		p_target_sdk = DEFAULT_TARGET_SDK_VERSION;
 	}
 	}
-	String exe_ext = "";
+	String exe_ext;
 	if (OS::get_singleton()->get_name() == "Windows") {
 	if (OS::get_singleton()->get_name() == "Windows") {
 		exe_ext = ".bat";
 		exe_ext = ".bat";
 	}
 	}
 	String apksigner_command_name = "apksigner" + exe_ext;
 	String apksigner_command_name = "apksigner" + exe_ext;
 	String sdk_path = EDITOR_GET("export/android/android_sdk_path");
 	String sdk_path = EDITOR_GET("export/android/android_sdk_path");
-	String apksigner_path = "";
+	String apksigner_path;
 
 
 	Error errn;
 	Error errn;
 	String build_tools_dir = sdk_path.path_join("build-tools");
 	String build_tools_dir = sdk_path.path_join("build-tools");
@@ -2329,6 +2338,32 @@ bool EditorExportPlatformAndroid::has_valid_export_configuration(const Ref<Edito
 		err += TTR("Release keystore incorrectly configured in the export preset.") + "\n";
 		err += TTR("Release keystore incorrectly configured in the export preset.") + "\n";
 	}
 	}
 
 
+	String java_sdk_path = EDITOR_GET("export/android/java_sdk_path");
+	if (java_sdk_path.is_empty()) {
+		err += TTR("A valid Java SDK path is required in Editor Settings.") + "\n";
+		valid = false;
+	} else {
+		// Validate the given path by checking that `java` is present under the `bin` directory.
+		Error errn;
+		// Check for the bin directory.
+		Ref<DirAccess> da = DirAccess::open(java_sdk_path.path_join("bin"), &errn);
+		if (errn != OK) {
+			err += TTR("Invalid Java SDK path in Editor Settings.");
+			err += TTR("Missing 'bin' directory!");
+			err += "\n";
+			valid = false;
+		} else {
+			// Check for the `java` command.
+			String java_path = get_java_path();
+			if (!FileAccess::exists(java_path)) {
+				err += TTR("Unable to find 'java' command using the Java SDK path.");
+				err += TTR("Please check the Java SDK directory specified in Editor Settings.");
+				err += "\n";
+				valid = false;
+			}
+		}
+	}
+
 	String sdk_path = EDITOR_GET("export/android/android_sdk_path");
 	String sdk_path = EDITOR_GET("export/android/android_sdk_path");
 	if (sdk_path.is_empty()) {
 	if (sdk_path.is_empty()) {
 		err += TTR("A valid Android SDK path is required in Editor Settings.") + "\n";
 		err += TTR("A valid Android SDK path is required in Editor Settings.") + "\n";
@@ -2861,6 +2896,13 @@ Error EditorExportPlatformAndroid::export_project_helper(const Ref<EditorExportP
 			}
 			}
 		}
 		}
 		const String assets_directory = get_assets_directory(p_preset, export_format);
 		const String assets_directory = get_assets_directory(p_preset, export_format);
+		String java_sdk_path = EDITOR_GET("export/android/java_sdk_path");
+		if (java_sdk_path.is_empty()) {
+			add_message(EXPORT_MESSAGE_ERROR, TTR("Export"), TTR("Java SDK path must be configured in Editor Settings at 'export/android/java_sdk_path'."));
+			return ERR_UNCONFIGURED;
+		}
+		print_verbose("Java sdk path: " + java_sdk_path);
+
 		String sdk_path = EDITOR_GET("export/android/android_sdk_path");
 		String sdk_path = EDITOR_GET("export/android/android_sdk_path");
 		if (sdk_path.is_empty()) {
 		if (sdk_path.is_empty()) {
 			add_message(EXPORT_MESSAGE_ERROR, TTR("Export"), TTR("Android SDK path must be configured in Editor Settings at 'export/android/android_sdk_path'."));
 			add_message(EXPORT_MESSAGE_ERROR, TTR("Export"), TTR("Android SDK path must be configured in Editor Settings at 'export/android/android_sdk_path'."));
@@ -2911,8 +2953,11 @@ Error EditorExportPlatformAndroid::export_project_helper(const Ref<EditorExportP
 		print_verbose("Storing command line flags...");
 		print_verbose("Storing command line flags...");
 		store_file_at_path(assets_directory + "/_cl_", command_line_flags);
 		store_file_at_path(assets_directory + "/_cl_", command_line_flags);
 
 
+		print_verbose("Updating JAVA_HOME environment to " + java_sdk_path);
+		OS::get_singleton()->set_environment("JAVA_HOME", java_sdk_path);
+
 		print_verbose("Updating ANDROID_HOME environment to " + sdk_path);
 		print_verbose("Updating ANDROID_HOME environment to " + sdk_path);
-		OS::get_singleton()->set_environment("ANDROID_HOME", sdk_path); //set and overwrite if required
+		OS::get_singleton()->set_environment("ANDROID_HOME", sdk_path);
 		String build_command;
 		String build_command;
 
 
 #ifdef WINDOWS_ENABLED
 #ifdef WINDOWS_ENABLED
@@ -2975,6 +3020,7 @@ Error EditorExportPlatformAndroid::export_project_helper(const Ref<EditorExportP
 		String combined_android_dependencies_maven_repos = String("|").join(android_dependencies_maven_repos);
 		String combined_android_dependencies_maven_repos = String("|").join(android_dependencies_maven_repos);
 
 
 		List<String> cmdline;
 		List<String> cmdline;
+		cmdline.push_back("validateJavaVersion");
 		if (clean_build_required) {
 		if (clean_build_required) {
 			cmdline.push_back("clean");
 			cmdline.push_back("clean");
 		}
 		}

+ 2 - 0
platform/android/export/export_plugin.h

@@ -226,6 +226,8 @@ public:
 
 
 	static String get_apksigner_path(int p_target_sdk = -1, bool p_check_executes = false);
 	static String get_apksigner_path(int p_target_sdk = -1, bool p_check_executes = false);
 
 
+	static String get_java_path();
+
 	virtual bool has_valid_export_configuration(const Ref<EditorExportPreset> &p_preset, String &r_error, bool &r_missing_templates, bool p_debug = false) const override;
 	virtual bool has_valid_export_configuration(const Ref<EditorExportPreset> &p_preset, String &r_error, bool &r_missing_templates, bool p_debug = false) const override;
 	virtual bool has_valid_project_configuration(const Ref<EditorExportPreset> &p_preset, String &r_error) const override;
 	virtual bool has_valid_project_configuration(const Ref<EditorExportPreset> &p_preset, String &r_error) const override;
 
 

+ 9 - 0
platform/android/java/app/build.gradle

@@ -241,3 +241,12 @@ task copyAndRenameReleaseAab(type: Copy) {
     into getExportPath()
     into getExportPath()
     rename "build-release.aab", getExportFilename()
     rename "build-release.aab", getExportFilename()
 }
 }
+
+/**
+ * Used to validate the version of the Java SDK used for the Godot gradle builds.
+ */
+task validateJavaVersion {
+    if (JavaVersion.current() != versions.javaVersion) {
+        throw new GradleException("Invalid Java version ${JavaVersion.current()}. Version ${versions.javaVersion} is the required Java version for Godot gradle builds.")
+    }
+}

+ 1 - 1
platform/android/java/app/config.gradle

@@ -9,7 +9,7 @@ ext.versions = [
     kotlinVersion      : '1.7.0',
     kotlinVersion      : '1.7.0',
     fragmentVersion    : '1.3.6',
     fragmentVersion    : '1.3.6',
     nexusPublishVersion: '1.1.0',
     nexusPublishVersion: '1.1.0',
-    javaVersion        : 17,
+    javaVersion        : JavaVersion.VERSION_17,
     // Also update 'platform/android/detect.py#get_ndk_version()' when this is updated.
     // Also update 'platform/android/detect.py#get_ndk_version()' when this is updated.
     ndkVersion         : '23.2.8568313'
     ndkVersion         : '23.2.8568313'