top.hendrixshen.magiclib.carpet.impl.WrappedSettingManager Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of magiclib-1_14_4 Show documentation
Show all versions of magiclib-1_14_4 Show documentation
To beat magic with magic :(
package top.hendrixshen.magiclib.carpet.impl;
import carpet.CarpetServer;
import carpet.settings.ParsedRule;
import com.google.common.collect.Lists;
import com.mojang.brigadier.CommandDispatcher;
import com.mojang.brigadier.arguments.StringArgumentType;
import com.mojang.brigadier.builder.LiteralArgumentBuilder;
import com.mojang.brigadier.context.CommandContext;
import com.mojang.brigadier.exceptions.CommandSyntaxException;
import com.mojang.brigadier.exceptions.SimpleCommandExceptionType;
import com.mojang.brigadier.suggestion.Suggestions;
import com.mojang.brigadier.suggestion.SuggestionsBuilder;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import top.hendrixshen.magiclib.MagicLibReference;
import top.hendrixshen.magiclib.carpet.api.CarpetExtensionCompatApi;
import top.hendrixshen.magiclib.carpet.api.annotation.Rule;
import top.hendrixshen.magiclib.carpet.mixin.accessor.SettingsManagerAccessor;
import top.hendrixshen.magiclib.compat.minecraft.api.network.chat.ComponentCompatApi;
import top.hendrixshen.magiclib.impl.carpet.MagicLibSettings;
import top.hendrixshen.magiclib.language.api.I18n;
import top.hendrixshen.magiclib.util.MessageUtil;
import top.hendrixshen.magiclib.util.ReflectUtil;
import java.lang.reflect.Field;
import java.nio.file.Path;
//#if MC <= 11802
//#endif
import java.util.*;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.stream.Collectors;
import net.minecraft.class_124;
import net.minecraft.class_2168;
import net.minecraft.class_2170;
import net.minecraft.class_2172;
import net.minecraft.class_2558;
import net.minecraft.class_2561;
import net.minecraft.class_2568;
//#if MC > 11404
//$$ import carpet.network.ServerNetworkHandler;
//#endif
//#if MC > 11502 && MC < 11904
//$$ import carpet.script.CarpetEventServer;
//#endif
//#if MC <= 11605
import org.apache.commons.lang3.tuple.Pair;
//#endif
//#if MC > 11900
//#if MC > 11903
//$$ import carpet.api.settings.CarpetRule;
//#endif
//$$ import carpet.api.settings.SettingsManager;
//$$ import net.minecraft.commands.CommandBuildContext;
//#else
import top.hendrixshen.magiclib.carpet.mixin.accessor.SettingsManagerAccessor;
//#if MC > 11502
//$$ import carpet.settings.Condition;
//#endif
import carpet.settings.SettingsManager;
//#endif
//#if MC >= 11901
//$$ @SuppressWarnings("removal")
//#endif
public class WrappedSettingManager extends SettingsManager {
private static final ConcurrentHashMap INSTANCES = new ConcurrentHashMap<>();
private final ConcurrentHashMap OPTIONS = new ConcurrentHashMap<>();
private final LinkedBlockingQueue CATEGORIES = new LinkedBlockingQueue<>();
private final ConcurrentHashMap, RuleOption> RULE_TO_OPTION = new ConcurrentHashMap<>();
private final String version;
private final String fancyName;
private final String identifier;
public static final String DEFAULT_LANGUAGE = "en_us";
private final List callbacks = Lists.newArrayList();
private static final List globalCallbacks = Lists.newArrayList();
public WrappedSettingManager(String version, String identifier, String fancyName) {
super(version, identifier, fancyName);
this.version = version;
this.identifier = identifier;
this.fancyName = fancyName;
}
public static WrappedSettingManager get(String identifier) {
return WrappedSettingManager.INSTANCES.get(identifier);
}
public static void printAllExtensionVersion(class_2168 source) {
WrappedSettingManager.INSTANCES.values().forEach(instance ->
MessageUtil.sendMessage(source, ComponentCompatApi.literal(instance.trUI("version", instance.trFancyName(), instance.getVersion()))
.method_10859(style -> style.method_10977(class_124.field_1080))));
}
public void registerRuleCallback(RuleCallback callback) {
this.callbacks.add(callback);// 136
}
public static void registerGlobalRuleCallback(RuleCallback callback) {
WrappedSettingManager.globalCallbacks.add(callback);// 150
}
public void onRuleChange(class_2168 source, @NotNull RuleOption rule, String value) {
this.callbacks.forEach(ruleCallback -> ruleCallback.callback(source, rule, value));
WrappedSettingManager.globalCallbacks.forEach(ruleCallback -> ruleCallback.callback(source, rule, value));
//#if MC > 11404
//$$ ServerNetworkHandler.updateRuleWithConnectedClients(rule.getRule());
//#endif
//#if MC > 11903
//$$ ReflectUtil.invokeDeclared("carpet.api.settings.SettingsManager",
//$$ "switchScarpetRuleIfNeeded", this,
//$$ new Class[]{CommandSourceStack.class, CarpetRule.class}, source, rule.getRule());
//#elseif MC > 11502
//$$ if (CarpetEventServer.Event.CARPET_RULE_CHANGES.isNeeded()) {
//$$ CarpetEventServer.Event.CARPET_RULE_CHANGES.onCarpetRuleChanges(rule.getRule(), source);
//$$ }
//#endif
}
public static void register(String identifier, T wrapperSettingsManager, CarpetExtensionCompatApi extension) {
if (WrappedSettingManager.INSTANCES.containsKey(identifier)) {
MagicLibReference.getLogger().error("SettingManager {} is registered", identifier);
}
CarpetServer.manageExtension(extension);
WrappedSettingManager.INSTANCES.put(identifier, wrapperSettingsManager);
}
public Collection getNonDefaultRuleOption() {
return this.OPTIONS.values().stream().filter(ruleOption -> !ruleOption.isDefault() && ruleOption.isEnabled())
.sorted(Comparator.comparing(RuleOption::getName)).collect(Collectors.toList());
}
// Compat for legacy Minecraft version.
public static boolean canUseCommand(class_2168 source, Object commandLevel) {
if (commandLevel instanceof Boolean) {
return (Boolean) commandLevel;
} else {
String commandLevelString = commandLevel.toString();
switch(commandLevelString) {
case "true":
return true;
case "ops":
return source.method_9259(2);
case "0":
case "1":
case "2":
case "3":
case "4":
return source.method_9259(Integer.parseInt(commandLevelString));
default:
return false;
}
}
}
//#if MC <= 11802
@SuppressWarnings("unchecked")
//#endif
@Override
public void parseSettingsClass(@NotNull Class settingsClass) {
for (Field field : settingsClass.getDeclaredFields()) {
Rule rule = field.getAnnotation(Rule.class);
if (rule == null) {
continue;
}
ReflectUtil.newInstance("carpet.settings.ParsedRule",
new Class[]{Field.class, Rule.class, WrappedSettingManager.class}, field, rule, this)
.ifPresent(o -> {
ParsedRule> carpetRule = (ParsedRule>) o;
RuleOption ruleOption = new RuleOption(rule, carpetRule);
for (String category : rule.categories()) {
if (!this.CATEGORIES.contains(category)) {
this.CATEGORIES.add(category);
}
}
//#if MC > 11802
//$$ this.addCarpetRule(carpetRule);
//#else
((SettingsManagerAccessor) this).getRules().put(carpetRule.name, carpetRule);
//#endif
this.OPTIONS.putIfAbsent(field.getName(), ruleOption);
this.RULE_TO_OPTION.putIfAbsent(carpetRule, ruleOption);
});
}
}
//#if MC > 11502
//$$ @Override
//#if MC > 11802
//$$ public void registerCommand(CommandDispatcher dispatcher, CommandBuildContext commandBuildContext) {
//#else
//$$ public void registerCommand(CommandDispatcher dispatcher) {
//#endif
//$$ this.registerCommandCompat(dispatcher);
//$$ }
//#endif
public void registerCommandCompat(@NotNull CommandDispatcher dispatcher) {
if (dispatcher.getRoot().getChildren().stream().anyMatch(node -> node.getName().equalsIgnoreCase(this.identifier))) {
MagicLibReference.getLogger().error("Failed to add settings command for {}. It is masking previous command.", this.identifier);
return;
}
LiteralArgumentBuilder command = class_2170.method_9247(this.identifier)
.requires(player -> WrappedSettingManager.canUseCommand(player, this.getSettingsManagerPermissionLevel()))
.executes(c -> this.displayMainMenu(c.getSource()))
.then(class_2170.method_9247("list")
.executes(c -> this.listAllSettings(c.getSource()))
.then(class_2170.method_9247("default")
.executes(c -> this.listDefaultSettings(c.getSource())))
.then(class_2170.method_9244("tags", StringArgumentType.word())
.suggests((c, b) -> class_2172.method_9264(this.getCategories().stream()
.filter(category -> this.getRuleOptionByCategory(category).stream().anyMatch(RuleOption::isEnabled)), b))
.executes(c -> this.listTagSettings(c.getSource(), StringArgumentType.getString(c, "tags")))))
.then(class_2170.method_9247("removeDefault")
.requires(s -> !this.locked())
.then(class_2170.method_9244("rule", StringArgumentType.word())
.suggests((c, b) -> class_2172.method_9264(this.OPTIONS.values().stream()
.filter(RuleOption::isEnabled).map(RuleOption::getName), b))
.executes(c -> this.removeDefault(c.getSource(), this.getRuleOption(c)))))
.then(class_2170.method_9247("setDefault")
.requires(s -> !this.locked())
.then(class_2170.method_9244("rule", StringArgumentType.word())
.suggests((c, b) -> class_2172.method_9264(this.OPTIONS.values().stream()
.filter(RuleOption::isEnabled).map(RuleOption::getName), b))
.then(class_2170.method_9244("value", StringArgumentType.greedyString())
.suggests(this::getRuleOptionSuggestion)
.executes(c -> this.setDefault(c.getSource(), this.getRuleOption(c), StringArgumentType.getString(c, "value"))))))
.then(class_2170.method_9244("rule", StringArgumentType.word())
.suggests((c, b) -> class_2172.method_9264(this.OPTIONS.values().stream()
.filter(RuleOption::isEnabled).map(RuleOption::getName), b))
.then(class_2170.method_9244("value", StringArgumentType.greedyString())
.requires(s -> !this.locked())
.suggests(this::getRuleOptionSuggestion)
.executes(c -> this.setRule(c.getSource(), this.getRuleOption(c), StringArgumentType.getString(c, "value"))))
.executes(c -> this.displayRuleMenu(c.getSource(), this.getRuleOption(c))))
.then(class_2170.method_9247("search")
.then(class_2170.method_9244("search", StringArgumentType.greedyString())
.executes(c -> this.searchRule(c.getSource(), StringArgumentType.getString(c, "search")))));
dispatcher.register(command);
}
private @Nullable CompletableFuture getRuleOptionSuggestion(CommandContext ctx, SuggestionsBuilder suggestionsBuilder) throws CommandSyntaxException {
RuleOption ruleOption = this.getRuleOption(ctx);
return ruleOption.isEnabled() ? class_2172.method_9265(this.getRuleOption(ctx)
.getOptions().stream().sorted().collect(Collectors.toList()), suggestionsBuilder) : null;
}
@Override
public Collection getCategories() {
return this.CATEGORIES;
}
public Collection getRuleOptions() {
return this.OPTIONS.values();
}
public RuleOption getRuleOption(String name) {
return this.OPTIONS.get(name);
}
public RuleOption getRuleOption(CommandContext ctx) throws CommandSyntaxException {
String ruleName = StringArgumentType.getString(ctx, "rule");
RuleOption ruleOption = this.getRuleOption(ruleName);
if (ruleOption == null) {
throw new SimpleCommandExceptionType(ComponentCompatApi.literal(this.trUI("unknown_rule", ruleName))
.method_10859(style -> style.method_10982(true).method_10977(class_124.field_1061))).create();
}
return ruleOption;
}
public RuleOption getRuleOption(ParsedRule> carpetRule) {
return this.RULE_TO_OPTION.get(carpetRule);
}
public Collection getRuleOptionByCategory(String category) {
return this.OPTIONS
.values()
.stream()
.filter(ruleOption -> Arrays.asList(ruleOption.getCategory()).contains(category))
.collect(Collectors.toList());
}
public String getSettingsManagerPermissionLevel() {
return MagicLibSettings.settingManagerLevel;
}
public String getCurrentLanguageCode() {
return MagicLibSettings.language;
}
public String getTranslatedRuleName(String ruleName) {
return (!this.getCurrentLanguageCode().equals(WrappedSettingManager.DEFAULT_LANGUAGE) &&
I18n.exists(this.getCurrentLanguageCode(), String.format("%s.rule.%s.name", this.identifier, ruleName))) ?
String.format("%s (%s)", this.trRuleName(ruleName), this.defaultRuleName(ruleName)) :
this.defaultRuleName(ruleName);
}
public String trFancyName() {
return I18n.exists(WrappedSettingManager.DEFAULT_LANGUAGE, String.format("%s.info.mod_name", this.identifier)) ?
this.trInfo("mod_name") : this.fancyName;
}
public String getIdentifier() {
return this.identifier;
}
public String getVersion() {
return this.version;
}
//#if MC <= 11802
public boolean locked() {
return this.locked;
}
//#endif
// The server side requires this way to use the fallback language.
public String tr(String code, String key, Object... objects) {
String value;
return (value = I18n.getByCode(code, key, objects)).equals(key) ? I18n.getByCode(WrappedSettingManager.DEFAULT_LANGUAGE, key, objects) : value;
}
// The server side requires this way to use the fallback language.
public String tr(String code, String key) {
String value;
return (value = I18n.getByCode(code, key)).equals(key) ? I18n.getByCode(WrappedSettingManager.DEFAULT_LANGUAGE, key) : value;
}
public String defaultRuleName(String ruleName) {
return I18n.exists(WrappedSettingManager.DEFAULT_LANGUAGE, String.format("%s.rule.%s.name", this.identifier, ruleName)) ?
this.tr(WrappedSettingManager.DEFAULT_LANGUAGE, String.format("%s.rule.%s.name", this.identifier, ruleName)) : ruleName;
}
public String trRuleName(String ruleName) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.rule.%s.name", this.identifier, ruleName));
}
public String trRuleDesc(String ruleName) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.rule.%s.desc", this.identifier, ruleName));
}
public String trCategory(String category) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.category.%s", this.identifier, category));
}
public String trInfo(String info) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.info.%s", this.identifier, info));
}
public String trValidator(String uiText) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.validator.%s", MagicLibReference.getModIdentifier(), uiText));
}
public String trValidator(String uiText, Object... objects) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.validator.%s", MagicLibReference.getModIdentifier(), uiText), objects);
}
public String trUI(String uiText) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.ui.%s", MagicLibReference.getModIdentifier(), uiText));
}
public String trUI(String uiText, Object... objects) {
return this.tr(this.getCurrentLanguageCode(), String.format("%s.ui.%s", MagicLibReference.getModIdentifier(), uiText), objects);
}
public List trRuleExtraInfo(String ruleName) {
List ret = Lists.newArrayList();
String key = String.format("%s.rule.%s.extra.%%d", this.identifier, ruleName);
for (int i = 0; I18n.exists(String.format(key, i)); i++) {
ret.add(ComponentCompatApi.literal(this.tr(this.getCurrentLanguageCode(), String.format(key, i))));
}
return ret;
}
public int displayRuleMenu(@NotNull class_2168 source, @NotNull RuleOption ruleOption) {
if (!ruleOption.isEnabled()) {
MessageUtil.sendMessage(source, trUI("disabled", ruleOption.getName()));
return 1;
}
MessageUtil.sendMessage(source, "");
MessageUtil.sendMessage(source, ComponentCompatApi.literal(this.getTranslatedRuleName(ruleOption.getName())).method_10859(
style -> style.method_10982(true)
.method_10958(new class_2558(class_2558.class_2559.field_11750, String.format("/%s %s", this.identifier, ruleOption.getName())))
.method_10949(new class_2568(class_2568.class_2569.field_11762, ComponentCompatApi.literal(this.trUI("hover.refresh"))
.method_10859(style1 -> style1.method_10977(class_124.field_1080))))));
MessageUtil.sendMessage(source, this.trRuleDesc(ruleOption.getName()));
this.trRuleExtraInfo(ruleOption.getName()).forEach(component ->
MessageUtil.sendMessage(source, component.method_10850().method_10859(style -> style.method_10977(class_124.field_1080))));
List categories = Lists.newArrayList();
categories.add(ComponentCompatApi.literal(this.trUI("tags")));
Arrays.stream(ruleOption.getCategory()).sorted().forEach(category -> {
categories.add(ComponentCompatApi.literal(String.format("[%s]", this.trCategory(category))).method_10859(style ->
style.method_10977(class_124.field_1075)
.method_10958(new class_2558(class_2558.class_2559.field_11750, String.format("/%s list %s", this.identifier, category)))
.method_10949(new class_2568(class_2568.class_2569.field_11762, ComponentCompatApi.literal(this.trUI("hover.list_all_category", category))))));
categories.add(ComponentCompatApi.literal(" "));
});
if (categories.size() > 1) {
categories.remove(categories.size() - 1);
} else {
categories.add(ComponentCompatApi.literal(this.trUI("null")).method_10859(style -> style.method_10977(class_124.field_1080)));
}
MessageUtil.sendMessage(source, categories);
List value = Lists.newArrayList();
value.add(ComponentCompatApi.literal(this.trUI("current_value")));
value.add(ComponentCompatApi.literal(String.format("%s (%s)", ruleOption.getValue(), ruleOption.isDefault() ?
this.trUI("default") : this.trUI("modified"))).method_10859(
style -> style.method_10982(true)
.method_10977(ruleOption.isDefault() ? class_124.field_1079 : class_124.field_1060)));
MessageUtil.sendMessage(source, value);
List options = Lists.newArrayList();
options.add(ComponentCompatApi.literal(this.trUI("options")));
options.add(ComponentCompatApi.literal("[ ").method_10859(style -> style.method_10977(class_124.field_1054)));
for (String option : ruleOption.getOptions()) {
options.add(ComponentCompatApi.literal(option).method_10859(style ->
style.withUnderlinedCompat(ruleOption.getStringValue().equals(option))
.method_10977(ruleOption.isDefault() ? class_124.field_1080 : ruleOption.getDefaultStringValue().equals(option) ? class_124.field_1077 : class_124.field_1054)
.method_10958(ruleOption.getStringValue().equals(option) || this.locked() ? null : new class_2558(class_2558.class_2559.field_11745, String.format("/%s %s %s", this.identifier, ruleOption.getName(), option)))
.method_10949(ruleOption.getStringValue().equals(option) || this.locked() ? null : new class_2568(class_2568.class_2569.field_11762, ComponentCompatApi.literal(this.trUI("hover.switch_to", option))))));
options.add(ComponentCompatApi.literal(" "));
}
if (options.size() > 2) {
options.remove(options.size() - 1);
}
options.add(ComponentCompatApi.literal(" ]").method_10859(style -> style.method_10977(class_124.field_1054)));
MessageUtil.sendMessage(source, options);
return 1;
}
public int setRule(class_2168 source, @NotNull RuleOption ruleOption, String newValue) {
if (!ruleOption.isEnabled()) {
MessageUtil.sendMessage(source, trUI("disabled", ruleOption.getName()));
return 1;
}
if (ruleOption.setValue(source, newValue) == null) {
return 1;
}
List components = Lists.newArrayList();
components.add(ComponentCompatApi.literal(String.format("%s: %s, ", this.getTranslatedRuleName(ruleOption.getName()), newValue)));
components.add(ComponentCompatApi.literal(String.format("[%s]", this.trUI("change_permanently")))
.method_10859(style -> style.method_10977(class_124.field_1075)
.method_10958(new class_2558(class_2558.class_2559.field_11750, String.format("/%s setDefault %s %s", this.identifier, ruleOption.getName(), newValue)))
.method_10949(new class_2568(class_2568.class_2569.field_11762, ComponentCompatApi.literal(this.trUI("hover.change_permanently", String.format("%s.conf",this.identifier)))))));
MessageUtil.sendMessage(source, components);
return 1;
}
@SuppressWarnings("unchecked")
public int setDefault(class_2168 source, RuleOption ruleOption, String newValue) {
if (this.locked()) {
MessageUtil.sendMessage(source, trUI("locked"));
return 1;
}
if (!ruleOption.isEnabled()) {
MessageUtil.sendMessage(source, trUI("disabled", ruleOption.getName()));
return 1;
}
if (ruleOption.setValue(source, newValue) == null) {
return 1;
}
Class> carpetSM = WrappedSettingManager.class.getSuperclass();
//#if MC > 11502
//$$ Path path = ((SettingsManagerAccessor) this).invokeGetFile();
//$$ Object conf = ReflectUtil.invokeDeclared(carpetSM, "readSettingsFromConf", this, new Class>[]{Path.class}, path).orElseThrow(RuntimeException::new);
//#else
Pair
© 2015 - 2025 Weber Informatics LLC | Privacy Policy