diff --git a/build.gradle b/build.gradle index d0edfa3..73d832c 100644 --- a/build.gradle +++ b/build.gradle @@ -9,11 +9,20 @@ base { archivesName = project.archives_base_name } +repositories { + maven { + name = "Terraformers" + url = "https://maven.terraformersmc.com/" + } +} + dependencies { minecraft "com.mojang:minecraft:${project.minecraft_version}" mappings "net.fabricmc:yarn:${project.yarn_mappings}:v2" modImplementation "net.fabricmc:fabric-loader:${project.loader_version}" modImplementation "net.fabricmc.fabric-api:fabric-api:${project.fabric_version}" + + modImplementation("com.terraformersmc:modmenu:16.0.0-rc.1") } processResources { diff --git a/src/main/java/com/kasetoatz/dumbassconfig/DumbassConfig.java b/src/main/java/com/kasetoatz/dumbassconfig/DumbassConfig.java index 58aa7b4..9a9be70 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/DumbassConfig.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/DumbassConfig.java @@ -1,10 +1,19 @@ package com.kasetoatz.dumbassconfig; -import com.kasetoatz.dumbassconfig.options.Option; +import com.google.gson.Gson; +import com.google.gson.GsonBuilder; +import com.google.gson.JsonObject; +import com.kasetoatz.dumbassconfig.options.AbstractOption; import com.kasetoatz.dumbassconfig.ui.ConfigScreen; +import net.fabricmc.loader.api.FabricLoader; import net.minecraft.client.gui.screen.Screen; import net.minecraft.text.Text; +import net.minecraft.util.crash.CrashException; +import net.minecraft.util.crash.CrashReport; +import java.io.IOException; +import java.nio.file.Files; +import java.nio.file.Path; import java.util.ArrayList; public class DumbassConfig @@ -24,8 +33,15 @@ public class DumbassConfig public static int BACKGROUND_COLOR_1 = 0x50555555; public static int BACKGROUND_COLOR_2 = 0x50333333; - private final ArrayList> options = new ArrayList<>(); + private final ArrayList> options = new ArrayList<>(); private ConfigScreen ui; + private final Path file; + private final Gson gson = new GsonBuilder().setPrettyPrinting().create(); + + private DumbassConfig(String filename) + { + this.file = FabricLoader.getInstance().getConfigDir().resolve(filename.endsWith(".json") ? filename : filename + ".json"); + } public Screen getUI(Screen parent) { @@ -33,9 +49,52 @@ public class DumbassConfig return this.ui; } - public static Builder builder(Text uiTitle) + private void load() { - return new Builder(uiTitle); + if (!Files.exists(this.file)) + { + this.save(); + return; + } + try + { + String json = Files.readString(this.file); + JsonObject data = this.gson.fromJson(json, JsonObject.class); + for (AbstractOption option : this.options) + { + if (data.has(option.getKey())) + { + option.fromJson(data.get(option.getKey())); + } + } + this.save(); + } + catch (IOException exc) + { + throw new CrashException(CrashReport.create(exc, "Loading config file.")); + } + } + + public void save() + { + try + { + JsonObject data = new JsonObject(); + for (AbstractOption option : this.options) + { + data.add(option.getKey(), this.gson.toJsonTree(option.getValue())); + } + Files.writeString(this.file, this.gson.toJson(data)); + } + catch (IOException exc) + { + throw new CrashException(CrashReport.create(exc, "Saving config file.")); + } + } + + public static Builder builder(Text uiTitle, String filename) + { + return new Builder(uiTitle, filename); } public static class Builder @@ -43,13 +102,13 @@ public class DumbassConfig private final DumbassConfig config; private final Text uiTitle; - private Builder(Text uiTitle) + private Builder(Text uiTitle, String filename) { - this.config = new DumbassConfig(); + this.config = new DumbassConfig(filename); this.uiTitle = uiTitle; } - public Builder withOption(Option option) + public Builder withOption(AbstractOption option) { this.config.options.add(option); return this; @@ -57,7 +116,9 @@ public class DumbassConfig public DumbassConfig build() { + this.config.load(); this.config.ui = new ConfigScreen(uiTitle, this.config.options); + this.config.ui.setSaveCallback(this.config::save); return this.config; } } diff --git a/src/main/java/com/kasetoatz/dumbassconfig/Test.java b/src/main/java/com/kasetoatz/dumbassconfig/Test.java new file mode 100644 index 0000000..0a7b368 --- /dev/null +++ b/src/main/java/com/kasetoatz/dumbassconfig/Test.java @@ -0,0 +1,23 @@ +package com.kasetoatz.dumbassconfig; + +import com.kasetoatz.dumbassconfig.options.BoolOption; +import com.kasetoatz.dumbassconfig.options.FloatOption; +import com.terraformersmc.modmenu.api.ConfigScreenFactory; +import com.terraformersmc.modmenu.api.ModMenuApi; +import net.minecraft.text.Text; + +public class Test implements ModMenuApi +{ + public static final BoolOption TEST_BOOL_OPT = new BoolOption("TEST", "test_bool_opt", false); + public static final FloatOption TEST_FLOAT_OPT = new FloatOption("TEST", "test_float_opt", 1.F); + DumbassConfig config = DumbassConfig.builder(Text.literal("Test Screen"), "test.json") + .withOption(TEST_BOOL_OPT) + .withOption(TEST_FLOAT_OPT) + .build(); + + @Override + public ConfigScreenFactory getModConfigScreenFactory() + { + return config::getUI; + } +} diff --git a/src/main/java/com/kasetoatz/dumbassconfig/options/ButtonOption.java b/src/main/java/com/kasetoatz/dumbassconfig/options/AbstractButtonOption.java similarity index 66% rename from src/main/java/com/kasetoatz/dumbassconfig/options/ButtonOption.java rename to src/main/java/com/kasetoatz/dumbassconfig/options/AbstractButtonOption.java index 86d8544..428b27f 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/options/ButtonOption.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/options/AbstractButtonOption.java @@ -3,9 +3,9 @@ package com.kasetoatz.dumbassconfig.options; import net.minecraft.client.gui.widget.ButtonWidget; import net.minecraft.text.Text; -public abstract class ButtonOption extends Option +public abstract class AbstractButtonOption extends AbstractOption { - public ButtonOption(String text, String key, T defaultValue) + public AbstractButtonOption(String text, String key, T defaultValue) { super(text, key, defaultValue); } diff --git a/src/main/java/com/kasetoatz/dumbassconfig/options/InputOption.java b/src/main/java/com/kasetoatz/dumbassconfig/options/AbstractInputOption.java similarity index 84% rename from src/main/java/com/kasetoatz/dumbassconfig/options/InputOption.java rename to src/main/java/com/kasetoatz/dumbassconfig/options/AbstractInputOption.java index d810591..ee56f66 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/options/InputOption.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/options/AbstractInputOption.java @@ -8,18 +8,18 @@ import net.minecraft.text.Text; import static com.kasetoatz.dumbassconfig.DumbassConfig.INVALID_INPUT_COLOR; import static com.kasetoatz.dumbassconfig.DumbassConfig.VALID_INPUT_COLOR; -public abstract class InputOption extends Option +public abstract class AbstractInputOption extends AbstractOption { public InputField textField; private Validator validator; - public InputOption(String text, String key, T defaultValue, Validator validator) + public AbstractInputOption(String text, String key, T defaultValue, Validator validator) { super(text, key, defaultValue); this.validator = validator; } - public InputOption(String text, String key, T defaultValue) + public AbstractInputOption(String text, String key, T defaultValue) { super(text, key, defaultValue); } diff --git a/src/main/java/com/kasetoatz/dumbassconfig/options/Option.java b/src/main/java/com/kasetoatz/dumbassconfig/options/AbstractOption.java similarity index 77% rename from src/main/java/com/kasetoatz/dumbassconfig/options/Option.java rename to src/main/java/com/kasetoatz/dumbassconfig/options/AbstractOption.java index 43acb58..463cb73 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/options/Option.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/options/AbstractOption.java @@ -1,15 +1,16 @@ package com.kasetoatz.dumbassconfig.options; +import com.google.gson.JsonElement; import net.minecraft.text.Text; -public abstract class Option +public abstract class AbstractOption { private final Text text; private final String key; private final T defaultValue; private T value; - public Option(String text, String key, T defaultValue) + public AbstractOption(String text, String key, T defaultValue) { this.text = Text.of(text); this.key = key; @@ -41,4 +42,6 @@ public abstract class Option { this.value = value; } + + public abstract void fromJson(JsonElement element); } diff --git a/src/main/java/com/kasetoatz/dumbassconfig/options/BoolOption.java b/src/main/java/com/kasetoatz/dumbassconfig/options/BoolOption.java index e6e5a7c..c6d2eb4 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/options/BoolOption.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/options/BoolOption.java @@ -1,12 +1,13 @@ package com.kasetoatz.dumbassconfig.options; +import com.google.gson.JsonElement; import net.minecraft.client.gui.widget.ButtonWidget; import net.minecraft.text.Text; import static com.kasetoatz.dumbassconfig.DumbassConfig.BOOLEAN_FALSE_COLOR; import static com.kasetoatz.dumbassconfig.DumbassConfig.BOOLEAN_TRUE_COLOR; -public class BoolOption extends ButtonOption +public class BoolOption extends AbstractButtonOption { public BoolOption(String text, String key, boolean defaultValue) { @@ -25,4 +26,10 @@ public class BoolOption extends ButtonOption this.setValue(!this.getValue()); button.setMessage(this.getButtonText()); } + + @Override + public void fromJson(JsonElement element) + { + this.setValue(element.getAsBoolean()); + } } diff --git a/src/main/java/com/kasetoatz/dumbassconfig/options/FloatOption.java b/src/main/java/com/kasetoatz/dumbassconfig/options/FloatOption.java index ae2650a..8a84644 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/options/FloatOption.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/options/FloatOption.java @@ -1,8 +1,9 @@ package com.kasetoatz.dumbassconfig.options; +import com.google.gson.JsonElement; import com.kasetoatz.dumbassconfig.options.validators.Validator; -public class FloatOption extends InputOption +public class FloatOption extends AbstractInputOption { public FloatOption(String text, String key, Float defaultValue, Validator validator) { @@ -37,4 +38,10 @@ public class FloatOption extends InputOption { this.onChange((text.isEmpty() || text.equals(".") || text.equals("-")) ? 0.F : Float.parseFloat(text)); } + + @Override + public void fromJson(JsonElement element) + { + this.setValue(element.getAsFloat()); + } } diff --git a/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigEntryList.java b/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigEntryList.java index fe48b2e..f8d7ca6 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigEntryList.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigEntryList.java @@ -1,8 +1,8 @@ package com.kasetoatz.dumbassconfig.ui; -import com.kasetoatz.dumbassconfig.options.ButtonOption; -import com.kasetoatz.dumbassconfig.options.InputOption; -import com.kasetoatz.dumbassconfig.options.Option; +import com.kasetoatz.dumbassconfig.options.AbstractButtonOption; +import com.kasetoatz.dumbassconfig.options.AbstractInputOption; +import com.kasetoatz.dumbassconfig.options.AbstractOption; import net.minecraft.client.MinecraftClient; import net.minecraft.client.gui.DrawContext; import net.minecraft.client.gui.widget.*; @@ -51,15 +51,15 @@ public class ConfigEntryList extends ElementListWidget super.renderWidget(context, mouseX, mouseY, delta); } - public void add(Option option) + public void add(AbstractOption option) { ConfigEntry entry = new ConfigEntry(); entry.add(new TextWidget(option.getText(), this.client.textRenderer)); - if (option instanceof ButtonOption buttonOption) + if (option instanceof AbstractButtonOption buttonOption) { entry.add(ButtonWidget.builder(buttonOption.getButtonText(), buttonOption::onClick).build()); } - else if (option instanceof InputOption inputOption) + else if (option instanceof AbstractInputOption inputOption) { inputOption.textField = new InputField(this.client.textRenderer, inputOption.getText()); inputOption.textField.setText(inputOption.getValue().toString()); diff --git a/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigScreen.java b/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigScreen.java index 3b5e0b5..a799b6f 100644 --- a/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigScreen.java +++ b/src/main/java/com/kasetoatz/dumbassconfig/ui/ConfigScreen.java @@ -1,6 +1,6 @@ package com.kasetoatz.dumbassconfig.ui; -import com.kasetoatz.dumbassconfig.options.Option; +import com.kasetoatz.dumbassconfig.options.AbstractOption; import net.minecraft.client.gui.screen.Screen; import net.minecraft.client.gui.widget.ButtonWidget; import net.minecraft.client.gui.widget.ThreePartsLayoutWidget; @@ -15,11 +15,12 @@ import static com.kasetoatz.dumbassconfig.DumbassConfig.ENTRY_HEIGHT; public class ConfigScreen extends Screen { private Screen parent; - private final List> options; + private final List> options; private final ThreePartsLayoutWidget layout = new ThreePartsLayoutWidget(this); private ConfigEntryList body; + private Runnable saveCallback; - public ConfigScreen(Text title, List> options) + public ConfigScreen(Text title, List> options) { super(title); this.options = options; @@ -30,12 +31,17 @@ public class ConfigScreen extends Screen this.parent = parent; } + public void setSaveCallback(Runnable callback) + { + this.saveCallback = callback; + } + @Override protected void init() { this.layout.addHeader(this.title, this.textRenderer); this.body = new ConfigEntryList(this.client, this.layout.getWidth(), this.layout.getContentHeight(), this.layout.getHeaderHeight(), ENTRY_HEIGHT); - for (Option option : this.options) + for (AbstractOption option : this.options) { this.body.add(option); } @@ -58,6 +64,7 @@ public class ConfigScreen extends Screen @Override public void close() { + this.saveCallback.run(); if (this.client != null) { this.client.setScreen(this.parent); diff --git a/src/main/resources/fabric.mod.json b/src/main/resources/fabric.mod.json index 8a55923..37f3703 100644 --- a/src/main/resources/fabric.mod.json +++ b/src/main/resources/fabric.mod.json @@ -9,6 +9,11 @@ "license": "MIT", "icon": "icon.png", "environment": "client", + "entrypoints": { + "modmenu": [ + "com.kasetoatz.dumbassconfig.Test" + ] + }, "depends": { "fabricloader": ">=${loader_version}", "fabric": "*",