diff --git a/common-files/src/main/resources/config.yml b/common-files/src/main/resources/config.yml index 4e33699a4..7947a3357 100644 --- a/common-files/src/main/resources/config.yml +++ b/common-files/src/main/resources/config.yml @@ -24,6 +24,8 @@ resource-pack: supported-version: min: server max: latest + # The description of your resource pack + description: "CraftEngine ResourcePack" # Remove 1.21.5+ tinted_leaves particles remove-tinted-leaves-particle: true # Define the name of the overlay folders @@ -65,7 +67,6 @@ resource-pack: path: "pack.mcmeta" resolution: type: merge_pack_mcmeta - description: "CraftEngine ResourcePack" - term: type: exact path: "pack.png" diff --git a/common-files/src/main/resources/resources/default/resourcepack/pack.mcmeta b/common-files/src/main/resources/resources/default/resourcepack/pack.mcmeta deleted file mode 100644 index 4d5e8390e..000000000 --- a/common-files/src/main/resources/resources/default/resourcepack/pack.mcmeta +++ /dev/null @@ -1,12 +0,0 @@ -{ - "pack": { - "pack_format": 15, - "description": "CraftEngine", - "supported_formats": { - "min_inclusive": 15, - "max_inclusive": 1000 - }, - "min_format": 15, - "max_format": 1000 - } -} \ No newline at end of file diff --git a/core/src/main/java/net/momirealms/craftengine/core/pack/AbstractPackManager.java b/core/src/main/java/net/momirealms/craftengine/core/pack/AbstractPackManager.java index f64c064f1..140421668 100644 --- a/core/src/main/java/net/momirealms/craftengine/core/pack/AbstractPackManager.java +++ b/core/src/main/java/net/momirealms/craftengine/core/pack/AbstractPackManager.java @@ -788,19 +788,28 @@ public abstract class AbstractPackManager implements PackManager { this.generateClientLang(generatedPackPath); this.generateEquipments(generatedPackPath, revisions::add); this.generateParticle(generatedPackPath); - this.generatePackMetadata(generatedPackPath.resolve("pack.mcmeta"), revisions); + + Path packMcMetaPath = generatedPackPath.resolve("pack.mcmeta"); + JsonObject packMcMeta = Files.isRegularFile(packMcMetaPath) ? GsonHelper.readJsonFile(packMcMetaPath).getAsJsonObject() : new JsonObject(); + // 生成revision overlay + this.generateRevisionOverlays(packMcMeta, revisions); + if (Config.excludeShaders()) { this.removeAllShaders(generatedPackPath); } long time2 = System.currentTimeMillis(); this.plugin.logger().info(TranslationManager.instance().translateLog("info.resource_pack.generate.finish", String.valueOf(time2 - time1))); + // 校验资源包 if (Config.validateResourcePack()) { - this.validateResourcePack(generatedPackPath); + this.validateResourcePack(generatedPackPath, packMcMeta); } long time3 = System.currentTimeMillis(); if (Config.validateResourcePack()) { this.plugin.logger().info(TranslationManager.instance().translateLog("info.resource_pack.validate.finish", String.valueOf(time3 - time2))); } + // 验证完成后,应该重新校验pack.mcmeta并写入 + this.validatePackMetadata(generatedPackPath.resolve("pack.mcmeta"), packMcMeta); + // 优化资源包 if (Config.optimizeResourcePack()) { this.optimizeResourcePack(generatedPackPath); } @@ -824,29 +833,61 @@ public abstract class AbstractPackManager implements PackManager { } } - private void generatePackMetadata(Path path, Set revisions) throws IOException { - JsonObject rawMeta; - boolean changed = false; - if (!Files.exists(path)) { - rawMeta = new JsonObject(); - changed = true; - } else { - rawMeta = GsonHelper.readJsonFile(path).getAsJsonObject(); - } - if (!rawMeta.has("pack")) { - JsonObject pack = new JsonObject(); - rawMeta.add("pack", pack); - pack.addProperty("pack_format", Config.packMinVersion().majorPackFormat()); - JsonObject supportedFormats = new JsonObject(); - supportedFormats.addProperty("min_inclusive", Config.packMinVersion().majorPackFormat()); - supportedFormats.addProperty("max_inclusive", Config.packMaxVersion().majorPackFormat()); - pack.add("supported_formats", supportedFormats); - changed = true; - } - if (revisions.isEmpty()) { - if (changed) { - GsonHelper.writeJsonFile(rawMeta, path); + private void validatePackMetadata(Path path, JsonObject rawMeta) throws IOException { + // 获取设定的最大和最小值 + PackVersion minVersion = Config.packMinVersion().packFormat(); + PackVersion maxVersion = Config.packMaxVersion().packFormat(); + + // 设置pack + { + JsonObject packJson = new JsonObject(); + rawMeta.add("pack", packJson); + JsonElement description = AdventureHelper.componentToJsonElement(AdventureHelper.miniMessage().deserialize(Config.packDescription())); + packJson.add("description", description); + // 需要旧版本兼容性 + if (minVersion.isBelow(PackVersion.PACK_FORMAT_CHANGE_VERSION)) { + packJson.addProperty("pack_format", minVersion.major()); + JsonObject supportedVersions = new JsonObject(); + supportedVersions.addProperty("min_inclusive", minVersion.major()); + supportedVersions.addProperty("max_inclusive", maxVersion.major()); + packJson.add("supported_formats", supportedVersions); } + // 到达了1.21.9 + if (maxVersion.isAtOrAbove(PackVersion.PACK_FORMAT_CHANGE_VERSION)) { + // 同时要兼容低版本 + packJson.add("min_format", minVersion.getAsJsonArray()); + packJson.add("max_format", maxVersion.getAsJsonArray()); + } + } + + // 验证overlay + { + PackMcMeta mcMeta = new PackMcMeta(rawMeta); + List overlays = mcMeta.overlays(); + if (!overlays.isEmpty()) { + boolean legacySupported = false; + for (Overlay overlay : overlays) { + if (overlay.minVersion().isBelow(PackVersion.PACK_FORMAT_CHANGE_VERSION)) { + legacySupported = true; + break; + } + } + JsonArray newOverlayEntries = new JsonArray(); + for (Overlay overlay : overlays) { + newOverlayEntries.add(overlay.getAsOverlayEntry(legacySupported)); + } + JsonObject overlaysJson = new JsonObject(); + overlaysJson.add("entries", newOverlayEntries); + rawMeta.add("overlays", overlaysJson); + } + } + + GsonHelper.writeJsonFile(rawMeta, path); + } + + // 这里都是随便写写的,重点在之后的校验里 + private void generateRevisionOverlays(JsonObject rawMeta, Set revisions) throws IOException { + if (revisions.isEmpty()) { return; } JsonObject overlays; @@ -865,18 +906,15 @@ public abstract class AbstractPackManager implements PackManager { } for (Revision revision : revisions) { JsonObject entry = new JsonObject(); - if (revision.minPackVersion().major() < 65) { - JsonArray formatsArray = new JsonArray(); - entry.add("formats", formatsArray); - formatsArray.add(revision.minPackVersion().major()); - formatsArray.add(revision.maxPackVersion().major()); - } + JsonArray formatsArray = new JsonArray(); + entry.add("formats", formatsArray); + formatsArray.add(revision.minPackVersion().major()); + formatsArray.add(revision.maxPackVersion().major()); entry.add("min_format", revision.minPackVersion().getAsJsonArray()); entry.add("max_format", revision.maxPackVersion().getAsJsonArray()); entry.addProperty("directory", Config.createOverlayFolderName(revision.versionString())); entries.add(entry); } - GsonHelper.writeJsonFile(rawMeta, path); } private void removeAllShaders(Path path) { @@ -1186,18 +1224,8 @@ public abstract class AbstractPackManager implements PackManager { } } - private void validateResourcePack(Path path) { - Path packMcMetaPath = path.resolve("pack.mcmeta"); - PackMcMeta packMeta; - JsonObject packMetaJson; - try { - packMetaJson = GsonHelper.readJsonFile(packMcMetaPath).getAsJsonObject(); - packMeta = new PackMcMeta(packMetaJson); - } catch (IOException e) { - this.plugin.logger().warn("Failed to read pack.mcmeta " + packMcMetaPath.toAbsolutePath(), e); - return; - } - + private void validateResourcePack(Path path, JsonObject packMetaJson) { + PackMcMeta packMeta = new PackMcMeta(packMetaJson); List segments = new ArrayList<>(); // 完全小于1.21.11或完全大于1.21.11 if (Config.packMaxVersion().isBelow(MinecraftVersion.V1_21_11) || Config.packMinVersion().isAtOrAbove(MinecraftVersion.V1_21_11)) { @@ -1292,7 +1320,7 @@ public abstract class AbstractPackManager implements PackManager { GsonHelper.writeJsonFile(entry.atlas(), atlasPath); if (!atlasToAdd.containsKey(directoryName)) { Overlay overlay = new Overlay(new PackVersion(min), new PackVersion(max), directoryName); - atlasToAdd.put(directoryName, overlay.getAsOverlayEntry()); + atlasToAdd.put(directoryName, overlay.getAsOverlayEntry(true)); } } catch (IOException e) { this.plugin.logger().warn("Failed to write atlas " + atlasPath.toAbsolutePath(), e); @@ -1326,7 +1354,7 @@ public abstract class AbstractPackManager implements PackManager { GsonHelper.writeJsonFile(entry.atlas(), atlasPath); if (!atlasToAdd.containsKey(directoryName)) { Overlay overlay = new Overlay(new PackVersion(min), new PackVersion(max), directoryName); - atlasToAdd.put(directoryName, overlay.getAsOverlayEntry()); + atlasToAdd.put(directoryName, overlay.getAsOverlayEntry(true)); } } catch (IOException e) { this.plugin.logger().warn("Failed to write atlas " + atlasPath.toAbsolutePath(), e); @@ -1347,11 +1375,6 @@ public abstract class AbstractPackManager implements PackManager { for (JsonElement entry : atlasToAdd.values()) { overlayEntries.add(entry); } - try { - GsonHelper.writeJsonFile(packMetaJson, packMcMetaPath); - } catch (IOException e) { - this.plugin.logger().warn("Failed to write pack.mcmeta", e); - } } } diff --git a/core/src/main/java/net/momirealms/craftengine/core/pack/conflict/resolution/ResolutionMergePackMcMeta.java b/core/src/main/java/net/momirealms/craftengine/core/pack/conflict/resolution/ResolutionMergePackMcMeta.java index 38063ac9e..ef7057ec0 100644 --- a/core/src/main/java/net/momirealms/craftengine/core/pack/conflict/resolution/ResolutionMergePackMcMeta.java +++ b/core/src/main/java/net/momirealms/craftengine/core/pack/conflict/resolution/ResolutionMergePackMcMeta.java @@ -9,7 +9,6 @@ import net.momirealms.craftengine.core.pack.conflict.PathContext; import net.momirealms.craftengine.core.pack.mcmeta.PackVersion; import net.momirealms.craftengine.core.plugin.CraftEngine; import net.momirealms.craftengine.core.plugin.config.Config; -import net.momirealms.craftengine.core.util.AdventureHelper; import net.momirealms.craftengine.core.util.GsonHelper; import net.momirealms.craftengine.core.util.Key; import net.momirealms.craftengine.core.util.Pair; @@ -26,13 +25,7 @@ public class ResolutionMergePackMcMeta implements Resolution { public static final Factory FACTORY = new Factory(); public static final Set STANDARD_PACK_KEYS = ImmutableSet.of("pack", "features", "filter", "overlays", "language"); - private final String description; - - public ResolutionMergePackMcMeta(String description) { - this.description = description; - } - - public static void merge(Path file1, Path file2, JsonElement customDescription) throws IOException { + public static void merge(Path file1, Path file2) throws IOException { // 第一步,解析全部的mcmeta文件为json对象 JsonObject mcmeta1; try { @@ -49,13 +42,15 @@ public class ResolutionMergePackMcMeta implements Resolution { return; } JsonObject merged = new JsonObject(); - // 第三步,处理pack区域 - JsonObject pack1 = mcmeta1.getAsJsonObject("pack"); - JsonObject pack2 = mcmeta2.getAsJsonObject("pack"); - JsonObject mergedPack = new JsonObject(); - mergedPack.add("description", customDescription); - merged.add("pack", mergedPack); - mergePack(mergedPack, pack1, pack2); + +// 注释: 无需处理,由后续验证合并 +// //第二步,处理pack区域 +// JsonObject pack1 = mcmeta1.getAsJsonObject("pack"); +// JsonObject pack2 = mcmeta2.getAsJsonObject("pack"); +// JsonObject mergedPack = new JsonObject(); +// merged.add("pack", mergedPack); +// mergePack(mergedPack, pack1, pack2); + // 第三步,合并overlays List overlays = new ArrayList<>(); collectOverlays(mcmeta1.getAsJsonObject("overlays"), overlays::add); @@ -165,14 +160,11 @@ public class ResolutionMergePackMcMeta implements Resolution { Pair supportedVersions = getSupportedVersions(entryJson); PackVersion min = PackVersion.getHigher(supportedVersions.left(), PackVersion.MIN_OVERLAY_VERSION); PackVersion max = PackVersion.getHigher(supportedVersions.right(), PackVersion.MIN_OVERLAY_VERSION); - // https://minecraft.wiki/w/Java_Edition_25w31a - if (min.major() < 65) { - // 旧版格式支持 - JsonArray supportedFormats = new JsonArray(); - supportedFormats.add(min.major()); - supportedFormats.add(max.major()); - entryJson.add("formats", supportedFormats); - } + // 旧版格式支持 + JsonArray supportedFormats = new JsonArray(); + supportedFormats.add(min.major()); + supportedFormats.add(max.major()); + entryJson.add("formats", supportedFormats); // 新版格式支持 JsonArray minFormat = new JsonArray(); minFormat.add(min.major()); @@ -285,7 +277,7 @@ public class ResolutionMergePackMcMeta implements Resolution { @Override public void run(PathContext existing, PathContext conflict) { try { - merge(existing.path(), conflict.path(), AdventureHelper.componentToJsonElement(AdventureHelper.miniMessage().deserialize(this.description))); + merge(existing.path(), conflict.path()); } catch (Exception e) { CraftEngine.instance().logger().severe("Failed to merge pack.mcmeta when resolving file conflicts for '" + existing.path() + "' and '" + conflict.path() + "'", e); } @@ -299,8 +291,7 @@ public class ResolutionMergePackMcMeta implements Resolution { public static class Factory implements ResolutionFactory { @Override public Resolution create(Map arguments) { - String description = arguments.getOrDefault("description", "CraftEngine ResourcePack").toString(); - return new ResolutionMergePackMcMeta(description); + return new ResolutionMergePackMcMeta(); } } } diff --git a/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/Overlay.java b/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/Overlay.java index b995fa8cd..a40b02acc 100644 --- a/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/Overlay.java +++ b/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/Overlay.java @@ -41,7 +41,7 @@ public class Overlay { '}'; } - public JsonObject getAsOverlayEntry() { + public JsonObject getAsOverlayEntry(boolean legacy) { JsonObject entry = new JsonObject(); entry.addProperty("directory", this.directory); JsonArray minFormat = new JsonArray(); @@ -52,7 +52,7 @@ public class Overlay { maxFormat.add(new JsonPrimitive(this.maxVersion.major())); maxFormat.add(new JsonPrimitive(this.maxVersion.minor())); entry.add("max_format", maxFormat); - if (this.minVersion.major() < 65) { + if (legacy) { JsonArray formats = new JsonArray(); formats.add(new JsonPrimitive(this.minVersion.major())); formats.add(new JsonPrimitive(this.maxVersion.major())); diff --git a/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/PackVersion.java b/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/PackVersion.java index 2e321e26f..4022e9bd5 100644 --- a/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/PackVersion.java +++ b/core/src/main/java/net/momirealms/craftengine/core/pack/mcmeta/PackVersion.java @@ -8,6 +8,7 @@ import java.util.List; public record PackVersion(int major, int minor) implements Comparable { public static final PackVersion MIN_PACK_VERSION = new PackVersion(15, 0); // 1.20 public static final PackVersion MIN_OVERLAY_VERSION = new PackVersion(18, 0); // 1.20 + public static final PackVersion PACK_FORMAT_CHANGE_VERSION = new PackVersion(65, 0); // 25w31a public static final PackVersion MAX_PACK_VERSION = new PackVersion(1000, 0); // future public PackVersion(int major) { diff --git a/core/src/main/java/net/momirealms/craftengine/core/plugin/config/Config.java b/core/src/main/java/net/momirealms/craftengine/core/plugin/config/Config.java index 49fbf150b..1c1b0d093 100644 --- a/core/src/main/java/net/momirealms/craftengine/core/plugin/config/Config.java +++ b/core/src/main/java/net/momirealms/craftengine/core/plugin/config/Config.java @@ -66,6 +66,7 @@ public class Config { protected List resource_pack$merge_external_zips; protected Set resource_pack$exclude_file_extensions; protected Path resource_pack$path; + protected String resource_pack$description; protected boolean resource_pack$protection$crash_tools$method_1; protected boolean resource_pack$protection$crash_tools$method_2; @@ -329,6 +330,7 @@ public class Config { // resource pack resource_pack$path = resolvePath(config.getString("resource-pack.path", "./generated/resource_pack.zip")); + resource_pack$description = config.getString("resource-pack.description", "CraftEngine ResourcePack"); resource_pack$override_uniform_font = config.getBoolean("resource-pack.override-uniform-font", false); resource_pack$generate_mod_assets = config.getBoolean("resource-pack.generate-mod-assets", false); resource_pack$remove_tinted_leaves_particle = config.getBoolean("resource-pack.remove-tinted-leaves-particle", true); @@ -1130,6 +1132,10 @@ public class Config { return instance.equipment$sacrificed_vanilla_armor$humanoid_leggings; } + public static String packDescription() { + return instance.resource_pack$description; + } + public static String sacrificedVanillaArmorType() { return instance.equipment$sacrificed_vanilla_armor$type; } diff --git a/gradle.properties b/gradle.properties index 0c853f64d..27f3fbb86 100644 --- a/gradle.properties +++ b/gradle.properties @@ -1,8 +1,8 @@ org.gradle.jvmargs=-Xmx4G # Project settings -project_version=0.0.66.5 -config_version=63 +project_version=0.0.66.6 +config_version=64 lang_version=46 project_group=net.momirealms latest_supported_version=1.21.11