package com.atsuishio.superbwarfare.data.launchable; import com.atsuishio.superbwarfare.Mod; import com.atsuishio.superbwarfare.data.gun.ProjectileInfo; import com.google.gson.Gson; import com.google.gson.JsonElement; import com.google.gson.JsonObject; import net.minecraft.nbt.*; import net.minecraft.server.packs.resources.ResourceManager; import net.neoforged.bus.api.SubscribeEvent; import net.neoforged.fml.common.EventBusSubscriber; import net.neoforged.neoforge.event.OnDatapackSyncEvent; import net.neoforged.neoforge.event.server.ServerStartedEvent; import org.jetbrains.annotations.Nullable; import java.io.InputStreamReader; import java.util.HashMap; import java.util.Locale; @EventBusSubscriber(modid = Mod.MODID) public class LaunchableEntityTool { public static HashMap launchableEntitiesData = new HashMap<>(); /** * 初始化数据,从data中读取数据json文件 */ public static void initJsonData(ResourceManager manager) { launchableEntitiesData.clear(); for (var entry : manager.listResources("launchable", file -> file.getPath().endsWith(".json")).entrySet()) { var attribute = entry.getValue(); try { Gson gson = new Gson(); var data = gson.fromJson(new InputStreamReader(attribute.open()), JsonObject.class); launchableEntitiesData.put(data.get("Type").getAsString(), data.get("Data").getAsJsonObject()); } catch (Exception e) { Mod.LOGGER.error(e.getMessage()); } } } public static @Nullable CompoundTag getModifiedTag(ProjectileInfo projectileInfo, ShootData data) { JsonObject launchableData; if (projectileInfo.data != null) { launchableData = projectileInfo.data; } else if (launchableEntitiesData.containsKey(projectileInfo.type)) { launchableData = launchableEntitiesData.get(projectileInfo.type); } else { return null; } var tag = new CompoundTag(); for (var d : launchableData.entrySet()) { var parsed = parseData(d.getValue(), data); if (parsed == null) continue; tag.put(d.getKey(), parsed); } return tag; } private static @Nullable Tag parseData(JsonElement object, ShootData data) { if (object.isJsonObject()) { var tag = new CompoundTag(); for (var d : object.getAsJsonObject().entrySet()) { var parsed = parseData(d.getValue(), data); if (parsed == null) continue; tag.put(d.getKey(), parsed); } return tag; } else if (object.isJsonArray()) { var tag = new ListTag(); for (var d : object.getAsJsonArray()) { tag.add(parseData(d, data)); } return tag; } else if (object.isJsonPrimitive()) { var prime = object.getAsJsonPrimitive(); if (prime.isString()) { return modifyStringTag(prime.getAsString(), data); } else if (prime.isNumber()) { return DoubleTag.valueOf(prime.getAsLong()); } else if (prime.isBoolean()) { return ByteTag.valueOf(prime.getAsBoolean()); } return null; } return null; } private static Tag modifyStringTag(String value, ShootData data) { return switch (value) { case "@sbw:damage" -> DoubleTag.valueOf(data.damage()); case "@sbw:owner" -> NbtUtils.createUUID(data.shooter()); case "@sbw:owner_string_lower" -> StringTag.valueOf(data.shooter().toString().replace("-", "").toLowerCase(Locale.ENGLISH)); case "@sbw:owner_string_upper" -> StringTag.valueOf(data.shooter().toString().replace("-", "").toUpperCase(Locale.ENGLISH)); case "@sbw:explosion_damage" -> DoubleTag.valueOf(data.explosionDamage()); case "@sbw:explosion_radius" -> DoubleTag.valueOf(data.explosionRadius()); case "@sbw:spread" -> DoubleTag.valueOf(data.spread()); default -> StringTag.valueOf(value); }; } @SubscribeEvent public static void serverStarted(ServerStartedEvent event) { initJsonData(event.getServer().getResourceManager()); } @SubscribeEvent public static void onDataPackSync(OnDatapackSyncEvent event) { initJsonData(event.getPlayerList().getServer().getResourceManager()); } }