Skip to content

Commit

Permalink
update structure upgrading
Browse files Browse the repository at this point in the history
  • Loading branch information
AViewFromTheTop committed Nov 5, 2024
1 parent dfd9059 commit db5bbf9
Show file tree
Hide file tree
Showing 6 changed files with 188 additions and 98 deletions.
12 changes: 8 additions & 4 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,11 @@ Make sure to clear this after each release
Put changelog here:

-----------------
- Fixed FrozenLib's capes causing severe performance issues when switching dimensions or respawning.
- Fixed `NbtFileUtils` creating a directory instead of a file.
- Added the `structure_upgrade` command, only accessible in development environments.
- This takes a string for the `namespace` parameter, and will grab all structure pieces under the given namespace then save them to `run/upgraded_structure,` upgraded to the latest DataVersion.
- Revamped the Structure NBT upgrading system.
- First, you must place the original structure NBT into the `structure/nbt_input` folder in the root of your project.
- This file path should be: `structure` -> `nbt_input` -> MOD ID -> STRUCTURE NAME
- Next, run `/structure snbt export {MOD ID}`.
- This will export all inputted NBT files under the mod id to SNBT.
- Finally, run `/structure snbt upgrade {MOD ID}`.
- This will place the fixed contents into the `nbt_output` folder.
- Copy the contents and paste them back into your structure data folder.
2 changes: 1 addition & 1 deletion src/main/java/net/frozenblock/lib/FrozenMain.java
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@
import net.frozenblock.lib.worldgen.feature.api.placementmodifier.FrozenPlacementModifiers;
import net.frozenblock.lib.worldgen.structure.impl.FrozenRuleBlockEntityModifiers;
import net.frozenblock.lib.worldgen.structure.impl.FrozenStructureProcessorTypes;
import net.frozenblock.lib.worldgen.structure.impl.StructureUpgradeCommand;
import net.frozenblock.lib.worldgen.structure.impl.command.StructureUpgradeCommand;
import net.frozenblock.lib.worldgen.surface.impl.BiomeTagConditionSource;
import net.frozenblock.lib.worldgen.surface.impl.OptimizedBiomeTagConditionSource;
import net.minecraft.commands.synchronization.ArgumentTypeInfos;
Expand Down
4 changes: 3 additions & 1 deletion src/main/java/net/frozenblock/lib/file/nbt/NbtFileUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,10 @@
package net.frozenblock.lib.file.nbt;

import com.mojang.logging.LogUtils;
import java.io.DataInputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import net.fabricmc.loader.api.FabricLoader;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.nbt.NbtIo;
Expand All @@ -38,7 +40,7 @@ public static void saveToConfigFile(CompoundTag compoundTag, String fileName) {
}

public static void saveToFile(CompoundTag compoundTag, @NotNull File file, String fileName) {
file.mkdirs();
file.getParentFile().mkdirs();
File destFile = new File(file, withNBTExtension(fileName));
saveToFile(compoundTag, destFile);
}
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,168 @@
/*
* Copyright (C) 2024 FrozenBlock
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/

package net.frozenblock.lib.worldgen.structure.impl.command;

import com.mojang.brigadier.CommandDispatcher;
import com.mojang.brigadier.arguments.StringArgumentType;
import net.frozenblock.lib.FrozenSharedConstants;
import net.minecraft.FileUtil;
import net.minecraft.commands.CommandSourceStack;
import net.minecraft.commands.Commands;
import net.minecraft.data.CachedOutput;
import net.minecraft.data.PackOutput;
import net.minecraft.data.structures.NbtToSnbt;
import net.minecraft.data.structures.SnbtToNbt;
import net.minecraft.data.structures.StructureUpdater;
import net.minecraft.network.chat.Component;
import net.minecraft.resources.ResourceLocation;
import net.minecraft.server.packs.resources.Resource;
import net.minecraft.server.packs.resources.ResourceManager;
import org.jetbrains.annotations.NotNull;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.CompletableFuture;

public class StructureUpgradeCommand {
private StructureUpgradeCommand() {}

public static void register(@NotNull CommandDispatcher<CommandSourceStack> dispatcher) {
dispatcher.register(Commands.literal("structure")
.then(Commands.literal("snbt")
.then(Commands.literal("export")
.then(Commands.argument("namespace", StringArgumentType.string())
.executes(context -> exportPiecesToSNBT(context.getSource(), StringArgumentType.getString(context, "namespace")))
)
)
.then(Commands.literal("upgrade")
.then(Commands.argument("namespace", StringArgumentType.string())
.executes(context -> exportSNBTToNBT(context.getSource(), StringArgumentType.getString(context, "namespace")))
)
)
)
.then(Commands.literal("piece")
.then(Commands.literal("count")
.then(Commands.argument("namespace", StringArgumentType.string())
.executes(context -> countPieces(context.getSource(), StringArgumentType.getString(context, "namespace")))
)
)
)
);
}

private static int exportPiecesToSNBT(@NotNull CommandSourceStack source, String namespace) {
try {
ResourceManager resourceManager = source.getServer().getResourceManager();

Set<ResourceLocation> foundPieces = resourceManager.listResources(
"structure",
resourceLocation -> resourceLocation.getPath().endsWith(".nbt") && resourceLocation.getNamespace().equals(namespace)
).keySet();

Path path = source.getServer().getServerDirectory();
if (path.getParent() != null) path = path.getParent();
path = path.resolve("structure");
Path inputPath = path.resolve("nbt_input");
Path outputPath = path.resolve("snbt");
outputPath.toFile().delete();
outputPath.toFile().mkdirs();

for (ResourceLocation resourceLocation : foundPieces) {
String putPath = resourceLocation.getNamespace() + "/" + resourceLocation.getPath().replaceFirst("structure/", "");
Path exportedPath = NbtToSnbt.convertStructure(CachedOutput.NO_CACHE, inputPath.resolve(putPath), putPath.replace(".nbt", ""), outputPath);
if (exportedPath != null) {
try {
FileUtil.createDirectoriesSafe(exportedPath.getParent());
} catch (IOException var7) {
FrozenSharedConstants.LOGGER.error("Could not create export folder", var7);
}
} else {
FrozenSharedConstants.LOGGER.error("Failed to export {}", resourceLocation);
}
}
long streamCount = Files.walk(outputPath).filter(p -> p.toString().endsWith(".snbt")).count();

if (streamCount > 0) {
source.sendSuccess(() -> Component.translatable("commands.frozenlib.structure_snbt.success", streamCount, foundPieces.size(), namespace), true);
} else {
source.sendSuccess(() -> Component.translatable("commands.frozenlib.structure_snbt.failure", namespace), true);
}
return 1;
} catch (Exception e) {
e.printStackTrace();
}
return 0;
}

private static int exportSNBTToNBT(@NotNull CommandSourceStack source, String namespace) {
try {
ResourceManager resourceManager = source.getServer().getResourceManager();

Map<ResourceLocation, Resource> foundPieces = resourceManager.listResources(
"structure",
resourceLocation -> resourceLocation.getPath().endsWith(".nbt") && resourceLocation.getNamespace().equals(namespace)
);

Path path = source.getServer().getServerDirectory();
if (path.getParent() != null) path = path.getParent();
path = path.resolve("structure");
Path inputPath = path.resolve("snbt");
Path outputPath = path.resolve("nbt_output");
outputPath.toFile().delete();
outputPath.toFile().mkdirs();

PackOutput packOutput = new PackOutput(outputPath);
SnbtToNbt snbtToNbt = new SnbtToNbt(packOutput, Set.of(inputPath)).addFilter(new StructureUpdater());
CompletableFuture completableFuture = snbtToNbt.run(CachedOutput.NO_CACHE);

while (!completableFuture.isDone()) {
}

long streamCount = Files.walk(outputPath).filter(p -> p.toString().endsWith(".nbt")).count();

if (streamCount > 0) {
source.sendSuccess(() -> Component.translatable("commands.frozenlib.structure_upgrade.success", streamCount, foundPieces.size(), namespace), true);
} else {
source.sendSuccess(() -> Component.translatable("commands.frozenlib.structure_upgrade.failure", namespace), true);
}
return 1;
} catch (Exception e) {
e.printStackTrace();
}
return 0;
}

private static int countPieces(@NotNull CommandSourceStack source, String namespace) {
ResourceManager resourceManager = source.getServer().getResourceManager();

Set<ResourceLocation> foundPieces = resourceManager.listResources(
"structure",
resourceLocation -> resourceLocation.getPath().endsWith(".nbt") && resourceLocation.getNamespace().equals(namespace)
).keySet();

int pieceCount = foundPieces.size();
if (pieceCount > 0) {
source.sendSuccess(() -> Component.translatable("commands.frozenlib.structure_piece_count.success", pieceCount, namespace), true);
} else {
source.sendSuccess(() -> Component.translatable("commands.frozenlib.structure_piece_count.failure", namespace), true);
}
return 1;
}
}
10 changes: 8 additions & 2 deletions src/main/resources/assets/frozenlib/lang/en_us.json
Original file line number Diff line number Diff line change
Expand Up @@ -81,8 +81,14 @@
"commands.frozenlib.taglist.footer": "Listed %s tags in %s.",
"commands.frozenlib.taglist.tag.invalid": "Invalid tag: %s",

"commands.structure_upgrade.success": "Upgraded and saved %s structure pieces for %s.",
"commands.structure_upgrade.failure": "No structure pieces found for %s.",
"commands.frozenlib.structure_snbt.success": "Exported %s of %s structure pieces to SNBT for %s.",
"commands.frozenlib.structure_snbt.failure": "No structure pieces found to export for %s.\nPlease copy structure NBT to structure/nbt_input in the root of your project.",

"commands.frozenlib.structure_upgrade.success": "Upgraded and saved %s of %s structure pieces for %s.",
"commands.frozenlib.structure_upgrade.failure": "No structure pieces found for %s.\nPlease run /structure snbt export first.",

"commands.frozenlib.structure_piece_count.success": "Found %s structure pieces for %s.",
"commands.frozenlib.structure_piece_count.failure": "No structure pieces found for %s.",

"commands.warden_spawn_tracker.clear.success.multiple": "Cleared warden spawn warnings from %s players",
"commands.warden_spawn_tracker.clear.success.single": "Cleared warden spawn warnings from %s",
Expand Down

0 comments on commit db5bbf9

Please sign in to comment.