fix liteloader & add controller
This commit is contained in:
parent
25b640609e
commit
ba77213394
|
@ -1 +1 @@
|
|||
2
|
||||
3
|
|
@ -1 +1 @@
|
|||
3
|
||||
4
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"name": "Default",
|
||||
"version": "1.0.0",
|
||||
"author": "Tungsten",
|
||||
"description": "Default controller of Fold Craft Launcher.",
|
||||
"controllerVersion": 0
|
||||
}
|
|
@ -64,12 +64,6 @@ public final class Config implements Cloneable, Observable {
|
|||
@SerializedName("commonpath")
|
||||
private StringProperty commonDirectory = new SimpleStringProperty(FCLPath.SHARED_COMMON_DIR);
|
||||
|
||||
@SerializedName("width")
|
||||
private DoubleProperty width = new SimpleDoubleProperty();
|
||||
|
||||
@SerializedName("height")
|
||||
private DoubleProperty height = new SimpleDoubleProperty();
|
||||
|
||||
@SerializedName("autoDownloadThreads")
|
||||
private BooleanProperty autoDownloadThreads = new SimpleBooleanProperty(false);
|
||||
|
||||
|
@ -166,30 +160,6 @@ public final class Config implements Cloneable, Observable {
|
|||
return commonDirectory;
|
||||
}
|
||||
|
||||
public double getWidth() {
|
||||
return width.get();
|
||||
}
|
||||
|
||||
public DoubleProperty widthProperty() {
|
||||
return width;
|
||||
}
|
||||
|
||||
public void setWidth(double width) {
|
||||
this.width.set(width);
|
||||
}
|
||||
|
||||
public double getHeight() {
|
||||
return height.get();
|
||||
}
|
||||
|
||||
public DoubleProperty heightProperty() {
|
||||
return height;
|
||||
}
|
||||
|
||||
public void setHeight(double height) {
|
||||
this.height.set(height);
|
||||
}
|
||||
|
||||
public boolean getAutoDownloadThreads() {
|
||||
return autoDownloadThreads.get();
|
||||
}
|
||||
|
|
|
@ -0,0 +1,218 @@
|
|||
package com.tungsten.fcl.setting;
|
||||
|
||||
import static com.tungsten.fcl.util.FXUtils.onInvalidating;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import com.google.gson.GsonBuilder;
|
||||
import com.google.gson.JsonDeserializationContext;
|
||||
import com.google.gson.JsonDeserializer;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonNull;
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.JsonParseException;
|
||||
import com.google.gson.JsonSerializationContext;
|
||||
import com.google.gson.JsonSerializer;
|
||||
import com.google.gson.annotations.JsonAdapter;
|
||||
import com.tungsten.fcl.util.Constants;
|
||||
import com.tungsten.fclauncher.FCLPath;
|
||||
import com.tungsten.fclcore.fakefx.beans.InvalidationListener;
|
||||
import com.tungsten.fclcore.fakefx.beans.Observable;
|
||||
import com.tungsten.fclcore.fakefx.beans.property.IntegerProperty;
|
||||
import com.tungsten.fclcore.fakefx.beans.property.ReadOnlyIntegerProperty;
|
||||
import com.tungsten.fclcore.fakefx.beans.property.SimpleIntegerProperty;
|
||||
import com.tungsten.fclcore.fakefx.beans.property.SimpleStringProperty;
|
||||
import com.tungsten.fclcore.fakefx.beans.property.StringProperty;
|
||||
import com.tungsten.fclcore.util.ToStringBuilder;
|
||||
import com.tungsten.fclcore.util.fakefx.ObservableHelper;
|
||||
import com.tungsten.fclcore.util.gson.fakefx.factories.JavaFxPropertyTypeAdapterFactory;
|
||||
import com.tungsten.fclcore.util.io.FileUtils;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.Optional;
|
||||
|
||||
@JsonAdapter(Controller.Serializer.class)
|
||||
public class Controller implements Observable {
|
||||
|
||||
private final SimpleStringProperty name;
|
||||
|
||||
public StringProperty nameProperty() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name.get();
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name.set(name);
|
||||
}
|
||||
|
||||
private final SimpleStringProperty version;
|
||||
|
||||
public StringProperty versionProperty() {
|
||||
return version;
|
||||
}
|
||||
|
||||
public String getVersion() {
|
||||
return version.get();
|
||||
}
|
||||
|
||||
public void setVersion(String version) {
|
||||
this.version.set(version);
|
||||
}
|
||||
|
||||
private final SimpleStringProperty author;
|
||||
|
||||
public StringProperty authorProperty() {
|
||||
return author;
|
||||
}
|
||||
|
||||
public String getAuthor() {
|
||||
return author.get();
|
||||
}
|
||||
|
||||
public void setAuthor(String author) {
|
||||
this.author.set(author);
|
||||
}
|
||||
|
||||
private final SimpleStringProperty description;
|
||||
|
||||
public StringProperty descriptionProperty() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description.get();
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description.set(description);
|
||||
}
|
||||
|
||||
private final IntegerProperty controllerVersion = new SimpleIntegerProperty(this, "controllerVersion");
|
||||
|
||||
public ReadOnlyIntegerProperty controllerVersionProperty() {
|
||||
return controllerVersion;
|
||||
}
|
||||
|
||||
public int getControllerVersion() {
|
||||
return controllerVersion.get();
|
||||
}
|
||||
|
||||
public Controller(String name) {
|
||||
this(name, "1.0.0");
|
||||
}
|
||||
|
||||
public Controller(String name, String version) {
|
||||
this(name, version, "");
|
||||
}
|
||||
|
||||
public Controller(String name, String version, String author) {
|
||||
this(name, version, author, "");
|
||||
}
|
||||
|
||||
public Controller(String name, String version, String author, String description) {
|
||||
this(name, version, author, description, Constants.CONTROLLER_VERSION);
|
||||
}
|
||||
|
||||
public Controller(String name, String version, String author, String description, int controllerVersion) {
|
||||
this.name = new SimpleStringProperty(this, "name", name);
|
||||
this.version = new SimpleStringProperty(this, "version", version);
|
||||
this.author = new SimpleStringProperty(this, "author", author);
|
||||
this.description = new SimpleStringProperty(this, "description", description);
|
||||
|
||||
this.controllerVersion.set(controllerVersion);
|
||||
|
||||
addPropertyChangedListener(onInvalidating(this::invalidate));
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public String toString() {
|
||||
return new ToStringBuilder(this)
|
||||
.append("name", getName())
|
||||
.append("version", getVersion())
|
||||
.append("author", getAuthor())
|
||||
.append("description", getDescription())
|
||||
.append("controllerVersion", getControllerVersion())
|
||||
.toString();
|
||||
}
|
||||
|
||||
private void addPropertyChangedListener(InvalidationListener listener) {
|
||||
name.addListener(listener);
|
||||
version.addListener(listener);
|
||||
author.addListener(listener);
|
||||
description.addListener(listener);
|
||||
controllerVersion.addListener(listener);
|
||||
}
|
||||
|
||||
private ObservableHelper observableHelper = new ObservableHelper(this);
|
||||
|
||||
@Override
|
||||
public void addListener(InvalidationListener listener) {
|
||||
observableHelper.addListener(listener);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeListener(InvalidationListener listener) {
|
||||
observableHelper.removeListener(listener);
|
||||
}
|
||||
|
||||
private void invalidate() {
|
||||
observableHelper.invalidate();
|
||||
}
|
||||
|
||||
// function
|
||||
|
||||
public String getFileName() {
|
||||
return getName() + ".json";
|
||||
}
|
||||
|
||||
public void saveToDisk() throws IOException {
|
||||
String str = new GsonBuilder()
|
||||
.registerTypeAdapterFactory(new JavaFxPropertyTypeAdapterFactory(true, true))
|
||||
.setPrettyPrinting()
|
||||
.create().toJson(this);
|
||||
FileUtils.writeText(new File(FCLPath.CONTROLLER_DIR, getFileName()), str);
|
||||
}
|
||||
|
||||
public void rename(String newName) throws IOException {
|
||||
FileUtils.copyFile(new File(FCLPath.CONTROLLER_DIR, getFileName()), new File(FCLPath.CONTROLLER_DIR, newName + ".json"));
|
||||
new File(FCLPath.CONTROLLER_DIR, getFileName()).delete();
|
||||
setName(newName);
|
||||
}
|
||||
|
||||
public static final class Serializer implements JsonSerializer<Controller>, JsonDeserializer<Controller> {
|
||||
@Override
|
||||
public JsonElement serialize(Controller src, Type typeOfSrc, JsonSerializationContext context) {
|
||||
if (src == null)
|
||||
return JsonNull.INSTANCE;
|
||||
|
||||
JsonObject jsonObject = new JsonObject();
|
||||
jsonObject.addProperty("name", src.getName());
|
||||
jsonObject.addProperty("version", src.getVersion());
|
||||
jsonObject.addProperty("author", src.getAuthor());
|
||||
jsonObject.addProperty("description", src.getDescription());
|
||||
jsonObject.addProperty("controllerVersion", src.getControllerVersion());
|
||||
|
||||
return jsonObject;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Controller deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException {
|
||||
if (json == JsonNull.INSTANCE || !(json instanceof JsonObject)) return null;
|
||||
JsonObject obj = (JsonObject) json;
|
||||
String name = Optional.ofNullable(obj.get("name")).map(JsonElement::getAsString).orElse("Error");
|
||||
String version = Optional.ofNullable(obj.get("version")).map(JsonElement::getAsString).orElse("1.0.0");
|
||||
String author = Optional.ofNullable(obj.get("author")).map(JsonElement::getAsString).orElse("");
|
||||
String description = Optional.ofNullable(obj.get("description")).map(JsonElement::getAsString).orElse("");
|
||||
int controllerVersion = Optional.ofNullable(obj.get("controllerVersion")).map(JsonElement::getAsInt).orElse(Constants.CONTROLLER_VERSION);
|
||||
|
||||
return new Controller(name, version, author, description, controllerVersion);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -0,0 +1,113 @@
|
|||
package com.tungsten.fcl.setting;
|
||||
|
||||
import static com.tungsten.fcl.util.FXUtils.onInvalidating;
|
||||
import static com.tungsten.fclcore.fakefx.collections.FXCollections.observableArrayList;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.GsonBuilder;
|
||||
import com.tungsten.fclauncher.FCLPath;
|
||||
import com.tungsten.fclcore.fakefx.beans.Observable;
|
||||
import com.tungsten.fclcore.fakefx.beans.property.ReadOnlyListProperty;
|
||||
import com.tungsten.fclcore.fakefx.beans.property.ReadOnlyListWrapper;
|
||||
import com.tungsten.fclcore.fakefx.collections.ObservableList;
|
||||
import com.tungsten.fclcore.util.Logging;
|
||||
import com.tungsten.fclcore.util.gson.fakefx.factories.JavaFxPropertyTypeAdapterFactory;
|
||||
import com.tungsten.fclcore.util.io.FileUtils;
|
||||
import com.tungsten.fclcore.util.io.IOUtils;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.logging.Level;
|
||||
|
||||
public class Controllers {
|
||||
|
||||
private Controllers() {
|
||||
}
|
||||
|
||||
private static final ObservableList<Controller> controllers = observableArrayList(controller -> new Observable[] { controller });
|
||||
private static final ReadOnlyListWrapper<Controller> controllersWrapper = new ReadOnlyListWrapper<>(controllers);
|
||||
|
||||
public static void checkControllers() {
|
||||
if (controllers.isEmpty()) {
|
||||
try {
|
||||
String str = IOUtils.readFullyAsString(Controllers.class.getResourceAsStream("/assets/controllers/Default.json"), StandardCharsets.UTF_8);
|
||||
Controller controller = new GsonBuilder()
|
||||
.registerTypeAdapterFactory(new JavaFxPropertyTypeAdapterFactory(true, true))
|
||||
.setPrettyPrinting()
|
||||
.create().fromJson(str, Controller.class);
|
||||
controller.saveToDisk();
|
||||
} catch (IOException e) {
|
||||
Logging.LOG.log(Level.SEVERE, "Failed to generate default controller!", e.getMessage());
|
||||
}
|
||||
controllers.addAll(getControllersFromDisk());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* True if {@link #init()} hasn't been called.
|
||||
*/
|
||||
private static boolean initialized = false;
|
||||
|
||||
private static void updateControllerStorages() {
|
||||
// don't update the underlying storage before data loading is completed
|
||||
// otherwise it might cause data loss
|
||||
if (!initialized)
|
||||
return;
|
||||
// update storage
|
||||
for (Controller controller : controllers) {
|
||||
try {
|
||||
controller.saveToDisk();
|
||||
} catch (IOException e) {
|
||||
Logging.LOG.log(Level.SEVERE, "Failed to save controller!");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static {
|
||||
controllers.addListener(onInvalidating(Controllers::updateControllerStorages));
|
||||
controllers.addListener(onInvalidating(Controllers::checkControllers));
|
||||
}
|
||||
|
||||
static void init() {
|
||||
if (initialized)
|
||||
throw new IllegalStateException("Already initialized");
|
||||
|
||||
getControllersFromDisk();
|
||||
controllers.addAll(getControllersFromDisk());
|
||||
checkControllers();
|
||||
|
||||
initialized = true;
|
||||
}
|
||||
|
||||
private static ArrayList<Controller> getControllersFromDisk() {
|
||||
ArrayList<Controller> list = new ArrayList<>();
|
||||
List<File> jsons = FileUtils.listFilesByExtension(new File(FCLPath.CONTROLLER_DIR), "json");
|
||||
for (File json : jsons) {
|
||||
if (json.isFile()) {
|
||||
try {
|
||||
String str = FileUtils.readText(json);
|
||||
Controller controller = new GsonBuilder()
|
||||
.registerTypeAdapterFactory(new JavaFxPropertyTypeAdapterFactory(true, true))
|
||||
.setPrettyPrinting()
|
||||
.create().fromJson(str, Controller.class);
|
||||
list.add(controller);
|
||||
} catch (IOException e) {
|
||||
Logging.LOG.log(Level.WARNING, "Can't read file: " + json.getAbsolutePath(), e.getMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
return list;
|
||||
}
|
||||
|
||||
public static ObservableList<Controller> getControllers() {
|
||||
return controllers;
|
||||
}
|
||||
|
||||
public static ReadOnlyListProperty<Controller> controllersProperty() {
|
||||
return controllersWrapper.getReadOnlyProperty();
|
||||
}
|
||||
|
||||
}
|
|
@ -28,6 +28,7 @@ public final class Settings {
|
|||
DownloadProviders.init();
|
||||
Accounts.init();
|
||||
Profiles.init();
|
||||
Controllers.init();
|
||||
AuthlibInjectorServers.init();
|
||||
|
||||
CacheRepository.setInstance(FCLCacheRepository.REPOSITORY);
|
||||
|
|
|
@ -341,6 +341,17 @@ public final class VersionSetting implements Cloneable {
|
|||
});
|
||||
}
|
||||
|
||||
public void checkController() {
|
||||
Controllers.checkControllers();
|
||||
|
||||
Controller controller = Controllers.getControllers().stream()
|
||||
.filter(it -> it.getName().equals(getController()))
|
||||
.findFirst()
|
||||
.orElse(Controllers.getControllers().get(0));
|
||||
|
||||
setController(controller.getName());
|
||||
}
|
||||
|
||||
public void addPropertyChangedListener(InvalidationListener listener) {
|
||||
usesGlobalProperty.addListener(listener);
|
||||
javaProperty.addListener(listener);
|
||||
|
|
|
@ -1,12 +1,24 @@
|
|||
package com.tungsten.fcl.ui.controller;
|
||||
|
||||
import android.content.Context;
|
||||
import android.view.View;
|
||||
import android.widget.ListView;
|
||||
|
||||
import androidx.appcompat.widget.LinearLayoutCompat;
|
||||
|
||||
import com.tungsten.fclcore.task.Task;
|
||||
import com.tungsten.fcllibrary.component.ui.FCLCommonUI;
|
||||
import com.tungsten.fcllibrary.component.view.FCLLinearLayout;
|
||||
import com.tungsten.fcllibrary.component.view.FCLUILayout;
|
||||
|
||||
public class ControllerUI extends FCLCommonUI {
|
||||
public class ControllerUI extends FCLCommonUI implements View.OnClickListener {
|
||||
|
||||
private ListView listView;
|
||||
|
||||
private LinearLayoutCompat importController;
|
||||
private LinearLayoutCompat createController;
|
||||
|
||||
private FCLLinearLayout infoLayout;
|
||||
|
||||
public ControllerUI(Context context, FCLUILayout parent, int id) {
|
||||
super(context, parent, id);
|
||||
|
@ -21,4 +33,9 @@ public class ControllerUI extends FCLCommonUI {
|
|||
public Task<?> refresh(Object... param) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onClick(View view) {
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
@ -273,6 +273,7 @@ public class VersionSettingPage extends FCLCommonPage implements ManageUI.Versio
|
|||
}
|
||||
|
||||
VersionSetting versionSetting = profile.getVersionSetting(versionId);
|
||||
versionSetting.checkController();
|
||||
|
||||
modpack.set(versionId != null && profile.getRepository().isModpack(versionId));
|
||||
usedMemory.set(MemoryUtils.getUsedDeviceMemory(getContext()));
|
||||
|
|
|
@ -95,15 +95,17 @@
|
|||
|
||||
</androidx.appcompat.widget.LinearLayoutCompat>
|
||||
|
||||
<ListView
|
||||
android:id="@+id/list"
|
||||
android:divider="@android:color/transparent"
|
||||
android:dividerHeight="0dp"
|
||||
<com.tungsten.fcllibrary.component.view.FCLLinearLayout
|
||||
android:id="@+id/info_layout"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="match_parent"
|
||||
app:layout_constraintHorizontal_bias="1"
|
||||
app:layout_constraintWidth_percent="0.7"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"/>
|
||||
app:layout_constraintEnd_toEndOf="parent">
|
||||
|
||||
|
||||
|
||||
</com.tungsten.fcllibrary.component.view.FCLLinearLayout>
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
|
@ -220,19 +220,9 @@ public interface GameRepository extends VersionProvider {
|
|||
default List<String> getClasspath(Version version) {
|
||||
List<String> classpath = new ArrayList<>();
|
||||
if (version.getMinimumLauncherVersion() >= 21) {
|
||||
// classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl.jar");
|
||||
// classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl-glfw.jar");
|
||||
// classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl-jemalloc.jar");
|
||||
// classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl-openal.jar");
|
||||
// classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl-opengl.jar");
|
||||
// classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl-stb.jar");
|
||||
// classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl-tinyfd.jar");
|
||||
classpath.add(FCLPath.LWJGL3_DIR + "/Lwjgl3.jar");
|
||||
}
|
||||
else {
|
||||
classpath.add(FCLPath.LWJGL2_DIR + "/Lwjgl2.jar");
|
||||
// classpath.add(FCLPath.LWJGL2_DIR + "/lwjgl.jar");
|
||||
// classpath.add(FCLPath.LWJGL2_DIR + "/lwjgl_util.jar");
|
||||
classpath.add(FCLPath.LWJGL3_DIR + "/lwjgl.jar");
|
||||
} else {
|
||||
classpath.add(FCLPath.LWJGL2_DIR + "/lwjgl.jar");
|
||||
}
|
||||
for (Library library : version.getLibraries())
|
||||
if (library.appliesToCurrentEnvironment() && !library.isNative()) {
|
||||
|
|
|
@ -15,7 +15,7 @@ public class LibFilter {
|
|||
public static List<Library> filterLibs(List<Library> libraries) {
|
||||
ArrayList<Library> newLibraries = new ArrayList<>();
|
||||
for (Library library : libraries) {
|
||||
if (!library.isNative() && !library.getName().contains("net.java.jinput") && !library.getName().contains("org.lwjgl") && !library.getName().contains("platform")) {
|
||||
if (!library.isNative() && !library.getName().contains("org.lwjgl") && !library.getName().contains("platform")) {
|
||||
newLibraries.add(library);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -25,6 +25,7 @@ public class FCLPath {
|
|||
public static String FILES_DIR;
|
||||
public static String PLUGIN_DIR;
|
||||
public static String BACKGROUND_DIR;
|
||||
public static String CONTROLLER_DIR;
|
||||
|
||||
public static String PRIVATE_COMMON_DIR;
|
||||
public static String SHARED_COMMON_DIR = Environment.getExternalStorageDirectory().getAbsolutePath() + "/FCL/.minecraft";
|
||||
|
@ -52,6 +53,7 @@ public class FCLPath {
|
|||
FILES_DIR = context.getFilesDir().getAbsolutePath();
|
||||
PLUGIN_DIR = FILES_DIR + "/plugins";
|
||||
BACKGROUND_DIR = FILES_DIR + "/background";
|
||||
CONTROLLER_DIR = FILES_DIR + "/control";
|
||||
|
||||
PRIVATE_COMMON_DIR = context.getExternalFilesDir(".minecraft").getAbsolutePath();
|
||||
|
||||
|
@ -71,6 +73,7 @@ public class FCLPath {
|
|||
init(FILES_DIR);
|
||||
init(PLUGIN_DIR);
|
||||
init(BACKGROUND_DIR);
|
||||
init(CONTROLLER_DIR);
|
||||
init(PRIVATE_COMMON_DIR);
|
||||
init(SHARED_COMMON_DIR);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue