Skip to content

Commit

Permalink
v2.0: Add ItemStack & /give + SNBT export
Browse files Browse the repository at this point in the history
  • Loading branch information
0KepOnline committed May 26, 2024
1 parent dfc4450 commit b54c191
Show file tree
Hide file tree
Showing 16 changed files with 804 additions and 246 deletions.
84 changes: 40 additions & 44 deletions build.gradle
Original file line number Diff line number Diff line change
@@ -1,38 +1,39 @@
plugins {
id 'fabric-loom' version '1.5-SNAPSHOT'
id 'maven-publish'
id 'fabric-loom' version '1.5-SNAPSHOT'
id 'maven-publish'
}

version = "${project.minecraft_version}-${project.mod_version}-fabric"
group = project.maven_group

base {
archivesName = project.mod_id
archivesName = project.mod_id
}

repositories {
// Add repositories to retrieve artifacts from in here.
// You should only use this when depending on other mods because
// Loom adds the essential maven repositories to download Minecraft and libraries from automatically.
// See https://docs.gradle.org/current/userguide/declaring_repositories.html
// for more information about repositories.
// Add repositories to retrieve artifacts from in here.
// You should only use this when depending on other mods because
// Loom adds the essential maven repositories to download Minecraft and libraries from automatically.
// See https://docs.gradle.org/current/userguide/declaring_repositories.html
// for more information about repositories.
}

dependencies {
// To change the versions see the gradle.properties file
minecraft "com.mojang:minecraft:${project.minecraft_version}"
mappings loom.officialMojangMappings()
modImplementation "net.fabricmc:fabric-loader:${project.loader_version}"
// To change the versions see the gradle.properties file
minecraft "com.mojang:minecraft:${project.minecraft_version}"
mappings loom.officialMojangMappings()
modImplementation "net.fabricmc:fabric-loader:${project.loader_version}"

// Fabric API. This is technically optional, but you probably want it anyway.
modImplementation "net.fabricmc.fabric-api:fabric-api:${project.fabric_version}"
// Fabric API. This is technically optional, but you probably want it anyway.
modImplementation "net.fabricmc.fabric-api:fabric-api:${project.fabric_version}"

// Uncomment the following line to enable the deprecated Fabric API modules.
// These are included in the Fabric API production distribution and allow you to update your mod to the latest modules at a later more convenient time.
// Uncomment the following line to enable the deprecated Fabric API modules.
// These are included in the Fabric API production distribution and allow you to update your mod to the latest modules at a later more convenient time.

// modImplementation "net.fabricmc.fabric-api:fabric-api-deprecated:${project.fabric_version}"
// modImplementation "net.fabricmc.fabric-api:fabric-api-deprecated:${project.fabric_version}"
}

def resourceTargets = ['fabric.mod.json']
def replaceProperties = [
minecraft_version: minecraft_version,
fabric_version: fabric_version,
Expand All @@ -42,47 +43,42 @@ def replaceProperties = [
mod_authors: mod_authors, mod_description: mod_description
]
processResources {
inputs.properties replaceProperties
inputs.properties replaceProperties
replaceProperties.put 'project', project

filesMatching("fabric.mod.json") {
expand replaceProperties
}
filesMatching(resourceTargets) {
expand replaceProperties
}
}

tasks.withType(JavaCompile).configureEach {
it.options.release = 17
it.options.release = 17
}

java {
// Loom will automatically attach sourcesJar to a RemapSourcesJar task and to the "build" task
// if it is present.
// If you remove this line, sources will not be generated.
withSourcesJar()

sourceCompatibility = JavaVersion.VERSION_17
targetCompatibility = JavaVersion.VERSION_17
sourceCompatibility = JavaVersion.VERSION_17
targetCompatibility = JavaVersion.VERSION_17
}

jar {
from("LICENSE") {
rename { "${it}_${base.archivesName.get()}"}
}
from("LICENSE") {
rename { "${it}_${base.archivesName.get()}"}
}
}

// configure the maven publication
publishing {
publications {
mavenJava(MavenPublication) {
from components.java
}
}
publications {
mavenJava(MavenPublication) {
from components.java
}
}

// See https://docs.gradle.org/current/userguide/publishing_maven.html for information on how to set up publishing.
repositories {
// Add repositories to publish to here.
// Notice: This block does NOT have the same function as the block in the top level.
// The repositories here will be used for publishing your artifact, not for
// retrieving dependencies.
}
// See https://docs.gradle.org/current/userguide/publishing_maven.html for information on how to set up publishing.
repositories {
// Add repositories to publish to here.
// Notice: This block does NOT have the same function as the block in the top level.
// The repositories here will be used for publishing your artifact, not for
// retrieving dependencies.
}
}
2 changes: 1 addition & 1 deletion gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ minecraft_version=1.19
loader_version=0.15.6

# Mod Properties
mod_version=1.2
mod_version=2.0
maven_group=net.scenariopla
mod_id=nbtexporter
mod_name=NBT Exporter
Expand Down
68 changes: 60 additions & 8 deletions src/main/java/net/scenariopla/nbtexporter/NBTExporter.java
Original file line number Diff line number Diff line change
@@ -1,40 +1,92 @@
package net.scenariopla.nbtexporter;

import java.io.File;
import java.nio.file.Files;
import java.text.SimpleDateFormat;
import java.util.regex.Pattern;

import net.fabricmc.api.ClientModInitializer;
import net.fabricmc.fabric.api.client.command.v2.ClientCommandRegistrationCallback;
import net.fabricmc.loader.api.FabricLoader;

import net.scenariopla.nbtexporter.command.ExportItemStackCommand;
import net.scenariopla.nbtexporter.command.ExportItemStackGiveCommand;
import net.scenariopla.nbtexporter.command.ExportItemStackNBTCommand;
import net.scenariopla.nbtexporter.command.ExportStringifiedItemStackCommand;
import net.scenariopla.nbtexporter.command.ExportStringifiedItemStackNBTCommand;
import net.scenariopla.nbtexporter.command.ICommand;
import net.scenariopla.nbtexporter.init.DirectoryInit;

public class NBTExporter implements ClientModInitializer {
public class Reference {
public static final String MODID = "nbtexporter";
public static final String MOD_ID = "nbtexporter";
public static final String NAME = "NBT Exporter";
public static final String VERSION = "1.2";
public static final String VERSION = "2.0";

public static final String MODDIR = MODID;
public static final String MOD_DIRECTORY = MOD_ID;

public static final ICommand[] MOD_CLIENT_COMMANDS = {
new ExportItemStackCommand(),
new ExportItemStackNBTCommand(),
new ExportStringifiedItemStackCommand(),
new ExportStringifiedItemStackNBTCommand(),
new ExportItemStackGiveCommand()
};

public static final FabricLoader MINECRAFT = FabricLoader.getInstance();
public static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyy-MM-dd_HH.mm.ss");

public static final String FILE_NAME_CHAR_REPLACE = "<>:\"/\\|?*\r\n\t\b\f";
public static final String FILE_NAME_CHAR_REPLACE = "<>:\"/\\\\|?*\r\n\t\b\f";
public static final Pattern FILE_NAME_CHAR_REPLACE_PATTERN = Pattern.compile("[" + FILE_NAME_CHAR_REPLACE + "]");
public static final char FILE_NAME_CHAR_REPLACE_NEW = '_';
}

public static File[] modDirFiles;
public static boolean simplifiedFilenameValidation;

public static void refreshModDir() {
modDirFiles = DirectoryInit.initModDirectory();
}

public static File[] modFiles = null;
private static void checkFilenameValidation() {
String fileStoreType;
String osName;
try {
fileStoreType = Files.getFileStore(DirectoryInit.modDir.toPath()).type().toLowerCase();
} catch (Exception e) {
e.printStackTrace();
fileStoreType = "";
}
try {
osName = System.getProperty("os.name").toLowerCase();
} catch (Exception e) {
e.printStackTrace();
osName = "";
}

simplifiedFilenameValidation = !fileStoreType.equals("ntfs") &&
!osName.contains("win") &&
!osName.contains("mac") &&
(fileStoreType.startsWith("ext") ||
fileStoreType.startsWith("ufs") ||
fileStoreType.equals("btrfs") ||
fileStoreType.equals("xfs") ||
fileStoreType.equals("zfs") ||
fileStoreType.equals("jfs") ||
fileStoreType.equals("qfs"));
}

@Override
public void onInitializeClient() {
ClientCommandRegistrationCallback.EVENT.register((dispatcher, registryAccess) -> {
ExportItemStackNBTCommand.register(dispatcher);
for (ICommand clientCommand : Reference.MOD_CLIENT_COMMANDS) {
clientCommand.register(dispatcher);
}
});

DirectoryInit.modDir = new File(Reference.MINECRAFT.getGameDir().toFile(), Reference.MODDIR);
modFiles = DirectoryInit.initModDirectory();
DirectoryInit.modDir = new File(Reference.MINECRAFT.getGameDir().toFile(),
Reference.MOD_DIRECTORY);
refreshModDir();
checkFilenameValidation();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
package net.scenariopla.nbtexporter.command;

import java.io.File;

import com.mojang.brigadier.CommandDispatcher;
import com.mojang.brigadier.arguments.StringArgumentType;
import com.mojang.brigadier.context.CommandContext;
import com.mojang.brigadier.exceptions.CommandSyntaxException;

import net.fabricmc.fabric.api.client.command.v2.FabricClientCommandSource;
import static net.fabricmc.fabric.api.client.command.v2.ClientCommandManager.argument;
import static net.fabricmc.fabric.api.client.command.v2.ClientCommandManager.literal;

import net.minecraft.nbt.CompoundTag;
import net.minecraft.network.chat.Component;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.item.ItemStack;

import net.scenariopla.nbtexporter.NBTExporter;
import net.scenariopla.nbtexporter.init.DirectoryInit;
import net.scenariopla.nbtexporter.util.FileSystemNamesakes;
import static net.scenariopla.nbtexporter.command.NBTExporterCommandExceptions.ExceptionCollection;
import static net.scenariopla.nbtexporter.command.NBTExporterCommandExceptions.exception;

public class ExportItemStackCommand extends NBTExporterCommand {
private static final String FILE_EXTENSION = ".stack.nbt";

private enum ExportItemStackExceptions implements ExceptionCollection {
SYNTAX_ERROR_USAGE("commands.nbtexporter.global.usage") {
@Override
public Object[] getArguments(Object[] args) {
return new Object[] {Component.translatable("commands.nbtexporter.exportstack.usage", args)};
}
};


private final String messageKey;
ExportItemStackExceptions(String messageKey) {
this.messageKey = messageKey;
}

@Override
public String getMessageKey() {
return messageKey;
}
}

public void register(CommandDispatcher<FabricClientCommandSource> dispatcher) {
dispatcher.register(literal("exportstack")
.executes(context -> {
return execute(context, getFilename());
})
.then(argument("filename", StringArgumentType.greedyString())
.suggests(globalSuggestion)
.requires(globalRequirement)
.executes(context -> {
return execute(context, getFilename(context, exception(ExportItemStackExceptions.SYNTAX_ERROR_USAGE)));
})));
}

private static int execute(CommandContext<FabricClientCommandSource> context,
String filename)
throws CommandSyntaxException {
final FabricClientCommandSource sourceStack = context.getSource();
NBTExporter.refreshModDir();

final Player player = (Player) sourceStack.getEntity();
final ItemStack heldItem = player.getMainHandItem();
if (heldItem.isEmpty()) {
throw exception(GlobalExceptions.HELD_ITEM_ERROR_EMPTY).create();
}

final CompoundTag nbtTagCompound = heldItem.save(new CompoundTag());

filename = FileSystemNamesakes.addIndex(filename,
FILE_EXTENSION,
NBTExporter.modDirFiles);

File outputFile = new File(DirectoryInit.modDir, filename);
outputFile = writeToFile(outputFile, nbtTagCompound);

final Component successMessage = Component.translatable("commands.nbtexporter.exportstack.success",
heldItem.getDisplayName(),
buildFileComponent(outputFile));
sourceStack.sendFeedback(successMessage);
return 1;
}
}
Loading

0 comments on commit b54c191

Please sign in to comment.