diff --git a/app/src/main/assets/components/ForgeInstallerHeadless/README.md b/app/src/main/assets/components/ForgeInstallerHeadless/README.md new file mode 100644 index 000000000..6de0d0432 --- /dev/null +++ b/app/src/main/assets/components/ForgeInstallerHeadless/README.md @@ -0,0 +1,3 @@ +From https://github.com/xfl03/ForgeInstallerHeadless +No changes on source code. + diff --git a/app/src/main/assets/components/ForgeInstallerHeadless/forge-installer-headless-1.0.1.jar b/app/src/main/assets/components/ForgeInstallerHeadless/forge-installer-headless-1.0.1.jar new file mode 100644 index 000000000..0449086d0 Binary files /dev/null and b/app/src/main/assets/components/ForgeInstallerHeadless/forge-installer-headless-1.0.1.jar differ diff --git a/app/src/main/java/net/kdt/pojavlaunch/JavaGUILauncherActivity.java b/app/src/main/java/net/kdt/pojavlaunch/JavaGUILauncherActivity.java index ed5ae0cf2..948c11a96 100644 --- a/app/src/main/java/net/kdt/pojavlaunch/JavaGUILauncherActivity.java +++ b/app/src/main/java/net/kdt/pojavlaunch/JavaGUILauncherActivity.java @@ -163,8 +163,11 @@ public class JavaGUILauncherActivity extends LoggableActivity { if (InstallerDetector.isForgeLegacy(installer)) { appendlnToLog("Detected Forge Installer 1.12.1 or below!"); return new LegacyForgeInstaller(installer).install(this); - } else if (InstallerDetector.isForgeNew(installer)) { - appendlnToLog("Detected Forge Installer 1.12.2 or above!"); + } else if (InstallerDetector.isForge1p12p2(installer)) { + appendlnToLog("Detected Forge Installer 1.12.2!"); + return new Legacy1p12p2ForgeInstaller(installer).install(this); + } else if (InstallerDetector.isForge1p12p2(installer)) { + appendlnToLog("Detected Forge Installer 1.13 or above!"); return new NewForgeInstaller(installer).install(this); } else if (InstallerDetector.isFabric(installer)) { appendlnToLog("Detected Fabric Installer!"); diff --git a/app/src/main/java/net/kdt/pojavlaunch/PojavLoginActivity.java b/app/src/main/java/net/kdt/pojavlaunch/PojavLoginActivity.java index 77a5dbddc..3b83da05c 100644 --- a/app/src/main/java/net/kdt/pojavlaunch/PojavLoginActivity.java +++ b/app/src/main/java/net/kdt/pojavlaunch/PojavLoginActivity.java @@ -363,18 +363,18 @@ public class PojavLoginActivity extends BaseActivity mkdirs(Tools.mpProfiles); mkdirs(Tools.MAIN_PATH); + mkdirs(Tools.MAIN_PATH + "/config"); mkdirs(Tools.MAIN_PATH + "/lwjgl3"); mkdirs(Tools.MAIN_PATH + "/mods"); File forgeSplashFile = new File(Tools.MAIN_PATH, "config/splash.properties"); - forgeSplashFile.mkdir(); String forgeSplashContent = "enabled=true"; try { if (forgeSplashFile.exists()) { forgeSplashContent = Tools.read(forgeSplashFile.toString()); } if (forgeSplashContent.contains("enabled=true")) { - Tools.write(forgeSplashFile.toString(), + Tools.write(forgeSplashFile.getAbsolutePath(), forgeSplashContent.replace("enabled=true", "enabled=false")); } } catch (IOException e) { @@ -384,8 +384,9 @@ public class PojavLoginActivity extends BaseActivity mkdirs(Tools.CTRLMAP_PATH); try { - AssetManager am = this.getAssets(); new CustomControls(this).save(Tools.CTRLDEF_FILE); + + Tools.copyAssetFile(this, "components/ForgeInstallerHeadless/forge-installer-headless.jar", Tools.MAIN_PATH + "/config", "forge-installer-headless.jar", true); Tools.copyAssetFile(this, "options.txt", Tools.MAIN_PATH, false); @@ -393,6 +394,8 @@ public class PojavLoginActivity extends BaseActivity // TODO: Remove after implement. Tools.copyAssetFile(this, "launcher_profiles.json", Tools.MAIN_PATH, false); + AssetManager am = this.getAssets(); + InputStream is = am.open("components/lwjgl3/version"); if(!new File(Tools.MAIN_PATH + "/lwjgl3/version").exists()) { Log.i("LWJGL3Prep","Pack was installed manually, or does not exist, unpacking new..."); diff --git a/app/src/main/java/net/kdt/pojavlaunch/Tools.java b/app/src/main/java/net/kdt/pojavlaunch/Tools.java index 5a6c37d27..54c14d473 100644 --- a/app/src/main/java/net/kdt/pojavlaunch/Tools.java +++ b/app/src/main/java/net/kdt/pojavlaunch/Tools.java @@ -312,24 +312,19 @@ public final class Tools return (scaledDp * currentDisplayMetrics.density); } - public static void copyAssetFile(Context ctx, String fileName, String output, boolean overwrite) throws Exception - { + public static void copyAssetFile(Context ctx, String fileName, String output, boolean overwrite) throws IOException { copyAssetFile(ctx, fileName, output, fileName, overwrite); } - public static void copyAssetFile(Context ctx, String fileName, String output, String outputName, boolean overwrite) throws Exception + public static void copyAssetFile(Context ctx, String fileName, String output, String outputName, boolean overwrite) throws IOException { - try { - File file = new File(output); - if(!file.exists()) { - file.mkdirs(); - } - File file2 = new File(output, outputName); - if(!file2.exists() || overwrite){ - write(file2.getAbsolutePath(), loadFromAssetToByte(ctx, fileName)); - } - } catch (Throwable th) { - throw new RuntimeException("Unable to copy " + fileName + " to " + output + "/" + outputName, th); + File file = new File(output); + if(!file.exists()) { + file.mkdirs(); + } + File file2 = new File(output, outputName); + if(!file2.exists() || overwrite){ + write(file2.getAbsolutePath(), loadFromAssetToByte(ctx, fileName)); } } /* diff --git a/app/src/main/java/net/kdt/pojavlaunch/installers/InstallerDetector.java b/app/src/main/java/net/kdt/pojavlaunch/installers/InstallerDetector.java index 789004d74..98af7ac90 100644 --- a/app/src/main/java/net/kdt/pojavlaunch/installers/InstallerDetector.java +++ b/app/src/main/java/net/kdt/pojavlaunch/installers/InstallerDetector.java @@ -16,7 +16,14 @@ public class InstallerDetector return profile != null && profile.versionInfo != null; } - // Forge New: for 1.12.2 and above + // Forge for 1.12.2 only + public static boolean isForge1p12p2(BaseInstaller installer) throws IOException, JsonSyntaxException { + ForgeInstallProfile profile = LegacyForgeInstaller.readInstallProfile(installer); + // Forge 1.12.2 install_profile.json has same format as Forge 1.13+ + return isForgeNew(installer) && profile.minecraft.equals("1.12.2"); + } + + // Forge New: for 1.13 and above public static boolean isForgeNew(BaseInstaller installer) throws IOException, JsonSyntaxException { ForgeInstallProfile profile = LegacyForgeInstaller.readInstallProfile(installer); return profile != null && profile.version != null; diff --git a/app/src/main/java/net/kdt/pojavlaunch/installers/Legacy1p12p2ForgeInstaller.java b/app/src/main/java/net/kdt/pojavlaunch/installers/Legacy1p12p2ForgeInstaller.java new file mode 100644 index 000000000..319b89ba1 --- /dev/null +++ b/app/src/main/java/net/kdt/pojavlaunch/installers/Legacy1p12p2ForgeInstaller.java @@ -0,0 +1,60 @@ +package net.kdt.pojavlaunch.installers; + +import android.content.*; +import java.io.*; +import java.util.jar.*; +import net.kdt.pojavlaunch.*; +import java.nio.charset.*; +import net.kdt.pojavlaunch.value.*; +import org.apache.commons.io.*; +import com.google.gson.*; +import java.util.zip.*; + +public class Legacy1p12p2ForgeInstaller extends BaseInstaller { + public Legacy1p12p2ForgeInstaller(BaseInstaller i) { + from(i); + } + + @Override + public int install(JavaGUILauncherActivity ctx) throws IOException { + String target; + + ctx.appendlnToLog("Reading install_profile.json"); + ForgeInstallProfile profile = readInstallProfile(this); + + // Write the json file + File versionFile = new File(Tools.versnDir, profile.version); + versionFile.mkdir(); + target = versionFile.getAbsolutePath() + "/" + profile.version + ".json"; + ctx.appendlnToLog("Writing " + target + " from " + profile.json); + ZipEntry versionJson = mJarFile.getEntry(profile.json==null ? "version.json" : profile.json.substring(profile.json.indexOf("/")+1,profile.json.length())); + Tools.write( + target, + Tools.convertStream(mJarFile.getInputStream(versionJson)) + ); + + // Forge 1.12.2+ installer does not include universal, so download + // Users are already go throught Forge ads to download installer, so not again. + String[] libInfos = profile.path.split(":"); + File libraryFile = new File(Tools.libraries, Tools.artifactToPath(libInfos[0], libInfos[1], libInfos[2])); + libraryFile.getParentFile().mkdirs(); + target = libraryFile.getAbsolutePath(); + String downloadPath = "https://files.minecraftforge.net/maven/" + profile.path.replace(":", "/").replace("net.minecraftforge","net/minecraftforge") + "/forge-" + libInfos[2] + "-universal.jar"; + ctx.appendlnToLog("Downloading " + target); + Tools.downloadFile(downloadPath, target); + + mJarFile.close(); + + return 0; + } + + public static ForgeInstallProfile readInstallProfile(BaseInstaller base) throws IOException, JsonSyntaxException { + ZipEntry entry = base.mJarFile.getEntry("install_profile.json"); + return entry == null ? null : Tools.GLOBAL_GSON.fromJson( + Tools.convertStream( + base.mJarFile.getInputStream(entry) + ), + ForgeInstallProfile.class + ); + } +} diff --git a/app/src/main/java/net/kdt/pojavlaunch/installers/NewForgeInstaller.java b/app/src/main/java/net/kdt/pojavlaunch/installers/NewForgeInstaller.java index 429c1e5ec..a4e56f909 100644 --- a/app/src/main/java/net/kdt/pojavlaunch/installers/NewForgeInstaller.java +++ b/app/src/main/java/net/kdt/pojavlaunch/installers/NewForgeInstaller.java @@ -1,60 +1,21 @@ package net.kdt.pojavlaunch.installers; -import android.content.*; import java.io.*; -import java.util.jar.*; import net.kdt.pojavlaunch.*; -import java.nio.charset.*; -import net.kdt.pojavlaunch.value.*; -import org.apache.commons.io.*; -import com.google.gson.*; -import java.util.zip.*; -public class NewForgeInstaller extends BaseInstaller { +public class NewForgeInstaller extends BaseInstaller + { public NewForgeInstaller(BaseInstaller i) { from(i); } @Override public int install(JavaGUILauncherActivity ctx) throws IOException { - String target; - - ctx.appendlnToLog("Reading install_profile.json"); - ForgeInstallProfile profile = readInstallProfile(this); - - // Write the json file - File versionFile = new File(Tools.versnDir, profile.version); - versionFile.mkdir(); - target = versionFile.getAbsolutePath() + "/" + profile.version + ".json"; - ctx.appendlnToLog("Writing " + target + " from " + profile.json); - ZipEntry versionJson = mJarFile.getEntry(profile.json==null ? "version.json" : profile.json.substring(profile.json.indexOf("/")+1,profile.json.length())); - Tools.write( - target, - Tools.convertStream(mJarFile.getInputStream(versionJson)) - ); - - // Forge 1.12.2+ installer does not include universal, so download - // Users are already go throught Forge ads to download installer, so not again. - String[] libInfos = profile.path.split(":"); - File libraryFile = new File(Tools.libraries, Tools.artifactToPath(libInfos[0], libInfos[1], libInfos[2])); - libraryFile.getParentFile().mkdirs(); - target = libraryFile.getAbsolutePath(); - String downloadPath = "https://files.minecraftforge.net/maven/" + profile.path.replace(":", "/").replace("net.minecraftforge","net/minecraftforge") + "/forge-" + libInfos[2] + "-universal.jar"; - ctx.appendlnToLog("Downloading " + target); - Tools.downloadFile(downloadPath, target); - + // Unused ZipFile mJarFile.close(); - - return 0; - } - public static ForgeInstallProfile readInstallProfile(BaseInstaller base) throws IOException, JsonSyntaxException { - ZipEntry entry = base.mJarFile.getEntry("install_profile.json"); - return entry == null ? null : Tools.GLOBAL_GSON.fromJson( - Tools.convertStream( - base.mJarFile.getInputStream(entry) - ), - ForgeInstallProfile.class - ); + ctx.appendlnToLog("Launching JVM"); + return ctx.launchJavaRuntime(null, + "-cp " + Tools.MAIN_PATH + "/config/forge-installer-headless.jar:" + mFile.getAbsolutePath() + " --installClient ."); } }