not done yet
This commit is contained in:
parent
79e0e2cbe4
commit
3b442fbee1
120
build.gradle
120
build.gradle
|
|
@ -1,7 +1,7 @@
|
||||||
plugins {
|
plugins {
|
||||||
id 'java-library'
|
id 'java-library'
|
||||||
id 'maven-publish'
|
id 'maven-publish'
|
||||||
id 'net.neoforged.moddev' version '2.0.86'
|
id 'net.neoforged.gradle.userdev' version '7.0.170'
|
||||||
id 'idea'
|
id 'idea'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -46,99 +46,50 @@ base {
|
||||||
archivesName = mod_id
|
archivesName = mod_id
|
||||||
}
|
}
|
||||||
|
|
||||||
// Mojang ships Java 17 to end users from 1.18 to 1.20.4, so your mod should target Java 17.
|
java.toolchain.languageVersion = JavaLanguageVersion.of(21)
|
||||||
java.toolchain.languageVersion = JavaLanguageVersion.of(17)
|
|
||||||
|
|
||||||
neoForge {
|
//parchment {
|
||||||
// Specify the version of NeoForge to use.
|
// mappingsVersion = project.parchment_mappings_version
|
||||||
version = project.neo_version
|
// minecraftVersion = project.parchment_minecraft_version
|
||||||
|
//}
|
||||||
|
|
||||||
parchment {
|
// accessTransformers = project.files('src/main/resources/META-INF/accesstransformer.cfg')
|
||||||
mappingsVersion = project.parchment_mappings_version
|
|
||||||
minecraftVersion = project.parchment_minecraft_version
|
runs {
|
||||||
|
configureEach {
|
||||||
|
|
||||||
|
systemProperty 'forge.logging.markers', 'REGISTRIES'
|
||||||
|
|
||||||
|
systemProperty 'forge.logging.console.level', 'debug'
|
||||||
|
|
||||||
|
modSource project.sourceSets.main
|
||||||
}
|
}
|
||||||
|
|
||||||
// This line is optional. Access Transformers are automatically detected
|
client {
|
||||||
// accessTransformers = project.files('src/main/resources/META-INF/accesstransformer.cfg')
|
client()
|
||||||
|
systemProperty 'neoforge.enabledGameTestNamespaces', project.mod_id
|
||||||
// Default run configurations.
|
|
||||||
// These can be tweaked, removed, or duplicated as needed.
|
|
||||||
runs {
|
|
||||||
client {
|
|
||||||
client()
|
|
||||||
|
|
||||||
// Comma-separated list of namespaces to load gametests from. Empty = all namespaces.
|
|
||||||
systemProperty 'neoforge.enabledGameTestNamespaces', project.mod_id
|
|
||||||
}
|
|
||||||
|
|
||||||
server {
|
|
||||||
server()
|
|
||||||
programArgument '--nogui'
|
|
||||||
systemProperty 'neoforge.enabledGameTestNamespaces', project.mod_id
|
|
||||||
}
|
|
||||||
|
|
||||||
// This run config launches GameTestServer and runs all registered gametests, then exits.
|
|
||||||
// By default, the server will crash when no gametests are provided.
|
|
||||||
// The gametest system is also enabled by default for other run configs under the /test command.
|
|
||||||
gameTestServer {
|
|
||||||
type = "gameTestServer"
|
|
||||||
systemProperty 'neoforge.enabledGameTestNamespaces', project.mod_id
|
|
||||||
}
|
|
||||||
|
|
||||||
data {
|
|
||||||
data()
|
|
||||||
|
|
||||||
// example of overriding the workingDirectory set in configureEach above, uncomment if you want to use it
|
|
||||||
// gameDirectory = project.file('run-data')
|
|
||||||
|
|
||||||
// Specify the modid for data generation, where to output the resulting resource, and where to look for existing resources.
|
|
||||||
programArguments.addAll '--mod', project.mod_id, '--all', '--output', file('src/generated/resources/').getAbsolutePath(), '--existing', file('src/main/resources/').getAbsolutePath()
|
|
||||||
}
|
|
||||||
|
|
||||||
// applies to all the run configs above
|
|
||||||
configureEach {
|
|
||||||
// Recommended logging data for a userdev environment
|
|
||||||
// The markers can be added/remove as needed separated by commas.
|
|
||||||
// "SCAN": For mods scan.
|
|
||||||
// "REGISTRIES": For firing of registry events.
|
|
||||||
// "REGISTRYDUMP": For getting the contents of all registries.
|
|
||||||
systemProperty 'forge.logging.markers', 'REGISTRIES'
|
|
||||||
|
|
||||||
// Recommended logging level for the console
|
|
||||||
// You can set various levels here.
|
|
||||||
// Please read: https://stackoverflow.com/questions/2031163/when-to-use-the-different-log-levels
|
|
||||||
logLevel = org.slf4j.event.Level.DEBUG
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
mods {
|
server {
|
||||||
// define mod <-> source bindings
|
server()
|
||||||
// these are used to tell the game which sources are for which mod
|
programArgument '--nogui'
|
||||||
// multi mod projects should define one per mod
|
systemProperty 'neoforge.enabledGameTestNamespaces', project.mod_id
|
||||||
"${mod_id}" {
|
}
|
||||||
sourceSet(sourceSets.main)
|
|
||||||
}
|
gameTestServer {
|
||||||
|
systemProperty 'neoforge.enabledGameTestNamespaces', project.mod_id
|
||||||
|
}
|
||||||
|
|
||||||
|
data {
|
||||||
|
programArguments.addAll '--mod', project.mod_id, '--all', '--output', file('src/generated/resources/').getAbsolutePath(), '--existing', file('src/main/resources/').getAbsolutePath()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Include resources generated by data generators.
|
// Include resources generated by data generators.
|
||||||
sourceSets.main.resources { srcDir 'src/generated/resources' }
|
sourceSets.main.resources { srcDir 'src/generated/resources' }
|
||||||
|
|
||||||
// Sets up a dependency configuration called 'localRuntime'.
|
|
||||||
// This configuration should be used instead of 'runtimeOnly' to declare
|
|
||||||
// a dependency that will be present for runtime testing but that is
|
|
||||||
// "optional", meaning it will not be pulled by dependents of this mod.
|
|
||||||
configurations {
|
|
||||||
runtimeClasspath.extendsFrom localRuntime
|
|
||||||
}
|
|
||||||
|
|
||||||
dependencies {
|
dependencies {
|
||||||
// Example optional mod dependency with JEI
|
implementation "net.neoforged:neoforge:${neo_version}"
|
||||||
// The JEI API is declared for compile time use, while the full JEI artifact is used at runtime
|
|
||||||
// compileOnly "mezz.jei:jei-${mc_version}-common-api:${jei_version}"
|
|
||||||
// compileOnly "mezz.jei:jei-${mc_version}-neoforge-api:${jei_version}"
|
|
||||||
// We add the full version to localRuntime, not runtimeOnly, so that we do not publish a dependency on it
|
|
||||||
// localRuntime "mezz.jei:jei-${mc_version}-neoforge:${jei_version}"
|
|
||||||
compileOnly "maven.modrinth:curios:7.4.3+1.20.4"
|
compileOnly "maven.modrinth:curios:7.4.3+1.20.4"
|
||||||
compileOnly "curse.maven:sophisticated-backpacks-422301:5297718"
|
compileOnly "curse.maven:sophisticated-backpacks-422301:5297718"
|
||||||
compileOnly "curse.maven:sophisticated-core-618298:5296142"
|
compileOnly "curse.maven:sophisticated-core-618298:5296142"
|
||||||
|
|
@ -157,7 +108,7 @@ dependencies {
|
||||||
// embedd the JDBC driver in the mod using jarJar
|
// embedd the JDBC driver in the mod using jarJar
|
||||||
runtimeOnly "com.mysql:mysql-connector-j:${jdbc_version}"
|
runtimeOnly "com.mysql:mysql-connector-j:${jdbc_version}"
|
||||||
jarJar "com.mysql:mysql-connector-j:${jdbc_version}"
|
jarJar "com.mysql:mysql-connector-j:${jdbc_version}"
|
||||||
additionalRuntimeClasspath "com.mysql:mysql-connector-j:${jdbc_version}"
|
// runtimeClasspath "com.mysql:mysql-connector-j:${jdbc_version}"
|
||||||
|
|
||||||
// For more info:
|
// For more info:
|
||||||
// http://www.gradle.org/docs/current/userguide/artifact_dependencies_tutorial.html
|
// http://www.gradle.org/docs/current/userguide/artifact_dependencies_tutorial.html
|
||||||
|
|
@ -185,11 +136,6 @@ var generateModMetadata = tasks.register("generateModMetadata", ProcessResources
|
||||||
from "src/main/templates"
|
from "src/main/templates"
|
||||||
into "build/generated/sources/modMetadata"
|
into "build/generated/sources/modMetadata"
|
||||||
}
|
}
|
||||||
// Include the output of "generateModMetadata" as an input directory for the build
|
|
||||||
// this works with both building through Gradle and the IDE.
|
|
||||||
sourceSets.main.resources.srcDir generateModMetadata
|
|
||||||
// To avoid having to run "generateModMetadata" manually, make it run on every project reload
|
|
||||||
neoForge.ideSyncTask generateModMetadata
|
|
||||||
|
|
||||||
// Example configuration to allow publishing using the maven-publish plugin
|
// Example configuration to allow publishing using the maven-publish plugin
|
||||||
publishing {
|
publishing {
|
||||||
|
|
|
||||||
|
|
@ -7,23 +7,19 @@ org.gradle.configuration-cache=true
|
||||||
|
|
||||||
#read more on this at https://github.com/neoforged/ModDevGradle?tab=readme-ov-file#better-minecraft-parameter-names--javadoc-parchment
|
#read more on this at https://github.com/neoforged/ModDevGradle?tab=readme-ov-file#better-minecraft-parameter-names--javadoc-parchment
|
||||||
# you can also find the latest versions at: https://parchmentmc.org/docs/getting-started
|
# you can also find the latest versions at: https://parchmentmc.org/docs/getting-started
|
||||||
parchment_minecraft_version=1.20.4
|
parchment_minecraft_version=1.21.1
|
||||||
parchment_mappings_version=2024.04.14
|
parchment_mappings_version=2024.11.17
|
||||||
# Environment Properties
|
# Environment Properties
|
||||||
# You can find the latest versions here: https://projects.neoforged.net/neoforged/neoforge
|
# You can find the latest versions here: https://projects.neoforged.net/neoforged/neoforge
|
||||||
# The Minecraft version must agree with the Neo version to get a valid artifact
|
# The Minecraft version must agree with the Neo version to get a valid artifact
|
||||||
minecraft_version=1.20.4
|
minecraft_version=1.21.1
|
||||||
# The Minecraft version range can use any release version of Minecraft as bounds.
|
# The Minecraft version range can use any release version of Minecraft as bounds.
|
||||||
# Snapshots, pre-releases, and release candidates are not guaranteed to sort properly
|
# Snapshots, pre-releases, and release candidates are not guaranteed to sort properly
|
||||||
# as they do not follow standard versioning conventions.
|
# as they do not follow standard versioning conventions.
|
||||||
minecraft_version_range=[1.20.4]
|
minecraft_version_range=[1.21,1.21.3)
|
||||||
# The Neo version must agree with the Minecraft version to get a valid artifact
|
neo_version=21.1.137
|
||||||
neo_version=20.4.248
|
neo_version_range=[21.1.128,)
|
||||||
# The Neo version range can use any version of Neo as bounds
|
loader_version_range=[4,)
|
||||||
neo_version_range=[20.4.248,)
|
|
||||||
# The loader version range can only use the major version of FML as bounds
|
|
||||||
loader_version_range=[1,)
|
|
||||||
|
|
||||||
## Mod Properties
|
## Mod Properties
|
||||||
|
|
||||||
# The unique mod identifier for the mod. Must be lowercase in English locale. Must fit the regex [a-z][a-z0-9_]{1,63}
|
# The unique mod identifier for the mod. Must be lowercase in English locale. Must fit the regex [a-z][a-z0-9_]{1,63}
|
||||||
|
|
|
||||||
|
|
@ -4,11 +4,11 @@ import com.mojang.brigadier.CommandDispatcher;
|
||||||
import net.minecraft.commands.CommandSourceStack;
|
import net.minecraft.commands.CommandSourceStack;
|
||||||
import net.minecraft.commands.Commands;
|
import net.minecraft.commands.Commands;
|
||||||
import net.neoforged.bus.api.SubscribeEvent;
|
import net.neoforged.bus.api.SubscribeEvent;
|
||||||
import net.neoforged.fml.common.Mod;
|
import net.neoforged.fml.common.EventBusSubscriber;
|
||||||
import net.neoforged.neoforge.event.RegisterCommandsEvent;
|
import net.neoforged.neoforge.event.RegisterCommandsEvent;
|
||||||
import vip.fubuki.playersync.sync.chat.ChatSyncClient;
|
import vip.fubuki.playersync.sync.chat.ChatSyncClient;
|
||||||
|
|
||||||
@Mod.EventBusSubscriber()
|
@EventBusSubscriber()
|
||||||
public class CommandInit {
|
public class CommandInit {
|
||||||
|
|
||||||
@SubscribeEvent
|
@SubscribeEvent
|
||||||
|
|
|
||||||
18
src/main/java/vip/fubuki/playersync/DataComponentTypes.java
Normal file
18
src/main/java/vip/fubuki/playersync/DataComponentTypes.java
Normal file
|
|
@ -0,0 +1,18 @@
|
||||||
|
package vip.fubuki.playersync;
|
||||||
|
|
||||||
|
import com.mojang.serialization.Codec;
|
||||||
|
import net.minecraft.core.component.DataComponentType;
|
||||||
|
import net.minecraft.core.registries.Registries;
|
||||||
|
import net.minecraft.network.codec.ByteBufCodecs;
|
||||||
|
import net.neoforged.neoforge.registries.DeferredHolder;
|
||||||
|
import net.neoforged.neoforge.registries.DeferredRegister;
|
||||||
|
|
||||||
|
public class DataComponentTypes {
|
||||||
|
public static final DeferredRegister<DataComponentType<?>> REGISTRY = DeferredRegister.create(Registries.DATA_COMPONENT_TYPE, PlayerSync.MODID);
|
||||||
|
public static final DeferredHolder<DataComponentType<?>, DataComponentType<String>> ORIGINAL_ITEM_NBT =
|
||||||
|
REGISTRY.register("original_item_nbt", () -> DataComponentType.<String>builder().persistent(Codec.STRING).networkSynchronized(ByteBufCodecs.STRING_UTF8).build());
|
||||||
|
public static final DeferredHolder<DataComponentType<?>, DataComponentType<String>> ORIGINAL_ITEM_ID =
|
||||||
|
REGISTRY.register("original_item_id", () -> DataComponentType.<String>builder().persistent(Codec.STRING).networkSynchronized(ByteBufCodecs.STRING_UTF8).build());
|
||||||
|
public static final DeferredHolder<DataComponentType<?>, DataComponentType<String>> UNIQUE_ID =
|
||||||
|
REGISTRY.register("unique_id", () -> DataComponentType.<String>builder().persistent(Codec.STRING).networkSynchronized(ByteBufCodecs.STRING_UTF8).build());
|
||||||
|
}
|
||||||
|
|
@ -1,6 +1,15 @@
|
||||||
package vip.fubuki.playersync;
|
package vip.fubuki.playersync;
|
||||||
|
|
||||||
import com.mojang.logging.LogUtils;
|
import com.mojang.logging.LogUtils;
|
||||||
|
import net.neoforged.bus.api.IEventBus;
|
||||||
|
import net.neoforged.bus.api.SubscribeEvent;
|
||||||
|
import net.neoforged.fml.ModContainer;
|
||||||
|
import net.neoforged.fml.ModList;
|
||||||
|
import net.neoforged.fml.common.Mod;
|
||||||
|
import net.neoforged.fml.config.ModConfig;
|
||||||
|
import net.neoforged.fml.event.lifecycle.FMLCommonSetupEvent;
|
||||||
|
import net.neoforged.neoforge.common.NeoForge;
|
||||||
|
import net.neoforged.neoforge.event.server.ServerStartingEvent;
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
import vip.fubuki.playersync.config.JdbcConfig;
|
import vip.fubuki.playersync.config.JdbcConfig;
|
||||||
import vip.fubuki.playersync.sync.ChatSync;
|
import vip.fubuki.playersync.sync.ChatSync;
|
||||||
|
|
@ -11,27 +20,17 @@ import java.sql.Connection;
|
||||||
import java.sql.ResultSet;
|
import java.sql.ResultSet;
|
||||||
import java.sql.SQLException;
|
import java.sql.SQLException;
|
||||||
import java.sql.Statement;
|
import java.sql.Statement;
|
||||||
import net.neoforged.bus.api.IEventBus;
|
|
||||||
import net.neoforged.bus.api.SubscribeEvent;
|
|
||||||
import net.neoforged.fml.ModList;
|
|
||||||
import net.neoforged.fml.ModLoadingContext;
|
|
||||||
import net.neoforged.fml.common.Mod;
|
|
||||||
import net.neoforged.fml.config.ModConfig;
|
|
||||||
import net.neoforged.fml.event.lifecycle.FMLCommonSetupEvent;
|
|
||||||
import net.neoforged.fml.javafmlmod.FMLJavaModLoadingContext;
|
|
||||||
import net.neoforged.neoforge.common.NeoForge;
|
|
||||||
import net.neoforged.neoforge.event.server.ServerStartingEvent;
|
|
||||||
import net.neoforged.bus.api.IEventBus;
|
|
||||||
|
|
||||||
@Mod(PlayerSync.MODID)
|
@Mod(PlayerSync.MODID)
|
||||||
public class PlayerSync {
|
public class PlayerSync {
|
||||||
public static final String MODID = "playersync";
|
public static final String MODID = "playersync";
|
||||||
public static final Logger LOGGER = LogUtils.getLogger();
|
public static final Logger LOGGER = LogUtils.getLogger();
|
||||||
|
|
||||||
public PlayerSync(IEventBus modEventBus) {
|
public PlayerSync(IEventBus modEventBus, ModContainer modContainer) {
|
||||||
|
DataComponentTypes.REGISTRY.register(modEventBus);
|
||||||
modEventBus.addListener(this::commonSetup);
|
modEventBus.addListener(this::commonSetup);
|
||||||
NeoForge.EVENT_BUS.register(this);
|
NeoForge.EVENT_BUS.register(this);
|
||||||
ModLoadingContext.get().registerConfig(ModConfig.Type.COMMON, JdbcConfig.COMMON_CONFIG);
|
modContainer.registerConfig(ModConfig.Type.COMMON, JdbcConfig.COMMON_CONFIG);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void commonSetup(final FMLCommonSetupEvent event) {
|
private void commonSetup(final FMLCommonSetupEvent event) {
|
||||||
|
|
|
||||||
|
|
@ -6,6 +6,11 @@ import net.minecraft.nbt.NbtUtils;
|
||||||
import net.minecraft.world.entity.player.Player;
|
import net.minecraft.world.entity.player.Player;
|
||||||
import net.minecraft.world.item.ItemStack;
|
import net.minecraft.world.item.ItemStack;
|
||||||
import net.neoforged.fml.ModList;
|
import net.neoforged.fml.ModList;
|
||||||
|
import net.neoforged.neoforge.server.ServerLifecycleHooks;
|
||||||
|
import top.theillusivec4.curios.api.CuriosApi;
|
||||||
|
import top.theillusivec4.curios.api.type.capability.ICuriosItemHandler;
|
||||||
|
import top.theillusivec4.curios.api.type.inventory.ICurioStacksHandler;
|
||||||
|
import top.theillusivec4.curios.api.type.inventory.IDynamicStackHandler;
|
||||||
import vip.fubuki.playersync.PlayerSync;
|
import vip.fubuki.playersync.PlayerSync;
|
||||||
import vip.fubuki.playersync.util.JDBCsetUp;
|
import vip.fubuki.playersync.util.JDBCsetUp;
|
||||||
import vip.fubuki.playersync.util.LocalJsonUtil;
|
import vip.fubuki.playersync.util.LocalJsonUtil;
|
||||||
|
|
@ -14,11 +19,6 @@ import java.sql.ResultSet;
|
||||||
import java.sql.SQLException;
|
import java.sql.SQLException;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
import top.theillusivec4.curios.api.CuriosApi;
|
|
||||||
import top.theillusivec4.curios.api.type.capability.ICuriosItemHandler;
|
|
||||||
import top.theillusivec4.curios.api.type.inventory.ICurioStacksHandler;
|
|
||||||
import top.theillusivec4.curios.api.type.inventory.IDynamicStackHandler;
|
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
|
|
@ -75,7 +75,7 @@ public class ModsSupport {
|
||||||
try {
|
try {
|
||||||
String nbtString = VanillaSync.deserializeString(serialized);
|
String nbtString = VanillaSync.deserializeString(serialized);
|
||||||
CompoundTag tag = NbtUtils.snbtToStructure(nbtString);
|
CompoundTag tag = NbtUtils.snbtToStructure(nbtString);
|
||||||
ItemStack stack = ItemStack.of(tag);
|
ItemStack stack = ItemStack.parse(ServerLifecycleHooks.getCurrentServer().registryAccess(),tag).get();
|
||||||
if (handler.getCurios().containsKey(slotType)) {
|
if (handler.getCurios().containsKey(slotType)) {
|
||||||
ICurioStacksHandler stacksHandler = handler.getCurios().get(slotType);
|
ICurioStacksHandler stacksHandler = handler.getCurios().get(slotType);
|
||||||
IDynamicStackHandler dynStacks = stacksHandler.getStacks();
|
IDynamicStackHandler dynStacks = stacksHandler.getStacks();
|
||||||
|
|
|
||||||
|
|
@ -2,8 +2,13 @@ package vip.fubuki.playersync.sync;
|
||||||
|
|
||||||
import com.mojang.brigadier.exceptions.CommandSyntaxException;
|
import com.mojang.brigadier.exceptions.CommandSyntaxException;
|
||||||
import net.minecraft.ChatFormatting;
|
import net.minecraft.ChatFormatting;
|
||||||
|
import net.minecraft.core.Holder;
|
||||||
|
import net.minecraft.core.HolderLookup;
|
||||||
|
import net.minecraft.core.component.DataComponents;
|
||||||
import net.minecraft.core.registries.BuiltInRegistries;
|
import net.minecraft.core.registries.BuiltInRegistries;
|
||||||
import net.minecraft.nbt.*;
|
import net.minecraft.nbt.CompoundTag;
|
||||||
|
import net.minecraft.nbt.NbtUtils;
|
||||||
|
import net.minecraft.nbt.Tag;
|
||||||
import net.minecraft.network.chat.Component;
|
import net.minecraft.network.chat.Component;
|
||||||
import net.minecraft.network.chat.Style;
|
import net.minecraft.network.chat.Style;
|
||||||
import net.minecraft.resources.ResourceLocation;
|
import net.minecraft.resources.ResourceLocation;
|
||||||
|
|
@ -17,15 +22,18 @@ import net.minecraft.world.entity.player.Inventory;
|
||||||
import net.minecraft.world.entity.player.Player;
|
import net.minecraft.world.entity.player.Player;
|
||||||
import net.minecraft.world.item.ItemStack;
|
import net.minecraft.world.item.ItemStack;
|
||||||
import net.minecraft.world.item.Items;
|
import net.minecraft.world.item.Items;
|
||||||
|
import net.minecraft.world.item.component.ItemLore;
|
||||||
import net.minecraft.world.level.storage.WorldData;
|
import net.minecraft.world.level.storage.WorldData;
|
||||||
import net.neoforged.bus.api.SubscribeEvent;
|
import net.neoforged.bus.api.SubscribeEvent;
|
||||||
import net.neoforged.fml.ModList;
|
import net.neoforged.fml.ModList;
|
||||||
import net.neoforged.fml.common.Mod;
|
import net.neoforged.fml.common.EventBusSubscriber;
|
||||||
import net.neoforged.neoforge.event.OnDatapackSyncEvent;
|
import net.neoforged.neoforge.event.OnDatapackSyncEvent;
|
||||||
import net.neoforged.neoforge.event.TickEvent;
|
|
||||||
import net.neoforged.neoforge.event.entity.player.PlayerEvent;
|
import net.neoforged.neoforge.event.entity.player.PlayerEvent;
|
||||||
import net.neoforged.neoforge.event.server.ServerStoppedEvent;
|
import net.neoforged.neoforge.event.server.ServerStoppedEvent;
|
||||||
|
import net.neoforged.neoforge.event.tick.LevelTickEvent;
|
||||||
|
import net.neoforged.neoforge.event.tick.ServerTickEvent;
|
||||||
import net.neoforged.neoforge.server.ServerLifecycleHooks;
|
import net.neoforged.neoforge.server.ServerLifecycleHooks;
|
||||||
|
import vip.fubuki.playersync.DataComponentTypes;
|
||||||
import vip.fubuki.playersync.PlayerSync;
|
import vip.fubuki.playersync.PlayerSync;
|
||||||
import vip.fubuki.playersync.config.JdbcConfig;
|
import vip.fubuki.playersync.config.JdbcConfig;
|
||||||
import vip.fubuki.playersync.util.JDBCsetUp;
|
import vip.fubuki.playersync.util.JDBCsetUp;
|
||||||
|
|
@ -42,7 +50,7 @@ import java.util.*;
|
||||||
import java.util.concurrent.ExecutorService;
|
import java.util.concurrent.ExecutorService;
|
||||||
import java.util.concurrent.Executors;
|
import java.util.concurrent.Executors;
|
||||||
|
|
||||||
@Mod.EventBusSubscriber
|
@EventBusSubscriber
|
||||||
public class VanillaSync {
|
public class VanillaSync {
|
||||||
|
|
||||||
public static void register() {}
|
public static void register() {}
|
||||||
|
|
@ -74,7 +82,7 @@ public class VanillaSync {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Restore Advancements
|
// Restore Advancements
|
||||||
File gameDir = Objects.requireNonNull(serverPlayer.getServer()).getServerDirectory();
|
File gameDir = Objects.requireNonNull(serverPlayer.getServer()).getServerDirectory().toFile();
|
||||||
|
|
||||||
final MinecraftServer server = ServerLifecycleHooks.getCurrentServer();
|
final MinecraftServer server = ServerLifecycleHooks.getCurrentServer();
|
||||||
if (server != null && server.isDedicatedServer()) {
|
if (server != null && server.isDedicatedServer()) {
|
||||||
|
|
@ -269,7 +277,7 @@ public class VanillaSync {
|
||||||
if (BuiltInRegistries.ITEM.containsKey(registryName)) {
|
if (BuiltInRegistries.ITEM.containsKey(registryName)) {
|
||||||
// Item exists (could be vanilla or a loaded mod item), restore normally
|
// Item exists (could be vanilla or a loaded mod item), restore normally
|
||||||
try {
|
try {
|
||||||
ItemStack restoredItem = ItemStack.of(compoundTag);
|
ItemStack restoredItem = ItemStack.parse(ServerLifecycleHooks.getCurrentServer().registryAccess(),compoundTag).get();
|
||||||
// Only return the restored item if the ItemStack.of did not unexpectedly
|
// Only return the restored item if the ItemStack.of did not unexpectedly
|
||||||
// returned an empty item
|
// returned an empty item
|
||||||
// Either the item is not empty, or it is empty and the original tag was also
|
// Either the item is not empty, or it is empty and the original tag was also
|
||||||
|
|
@ -293,29 +301,24 @@ public class VanillaSync {
|
||||||
PlayerSync.LOGGER.debug("Item {} not found in registry. Creating placeholder.", registryName);
|
PlayerSync.LOGGER.debug("Item {} not found in registry. Creating placeholder.", registryName);
|
||||||
ItemStack placeholder = new ItemStack(Items.PAPER);
|
ItemStack placeholder = new ItemStack(Items.PAPER);
|
||||||
|
|
||||||
CompoundTag placeholderNbt = placeholder.getOrCreateTag();
|
|
||||||
// Store the original serialized NBT string, not the parsed CompoundTag string
|
// Store the original serialized NBT string, not the parsed CompoundTag string
|
||||||
placeholderNbt.putString("playersync:original_item_nbt", serializedNbt);
|
placeholder.set(DataComponentTypes.ORIGINAL_ITEM_NBT.get(), serializedNbt);
|
||||||
placeholderNbt.putString("playersync:original_item_id", registryName.toString());
|
placeholder.set(DataComponentTypes.ORIGINAL_ITEM_ID.get(), registryName.toString());
|
||||||
|
|
||||||
// Add a unique UUID to ensure the item is unstackable
|
// Add a unique UUID to ensure the item is unstackable
|
||||||
// Stacked placerholders would be converted into a single item when restoring item
|
// Stacked placerholders would be converted into a single item when restoring item
|
||||||
placeholderNbt.putUUID("playersync:unique_id", UUID.randomUUID());
|
placeholder.set(DataComponentTypes.UNIQUE_ID.get(), UUID.randomUUID().toString());
|
||||||
|
|
||||||
// Add display name and lore
|
// Add display name and lore
|
||||||
CompoundTag displayTag = placeholderNbt.getCompound("display");
|
|
||||||
if (!placeholderNbt.contains("display"))
|
|
||||||
placeholderNbt.put("display", displayTag);
|
|
||||||
|
|
||||||
String placeholderItemTitleOverride = JdbcConfig.ITEM_PLACEHOLDER_TITLE_OVERRIDE.get();
|
String placeholderItemTitleOverride = JdbcConfig.ITEM_PLACEHOLDER_TITLE_OVERRIDE.get();
|
||||||
displayTag.putString("Name", Component.Serializer.toJson(
|
placeholder.set(DataComponents.ITEM_NAME,
|
||||||
Component
|
Component
|
||||||
.literal(placeholderItemTitleOverride != null && !placeholderItemTitleOverride.isBlank()
|
.literal(placeholderItemTitleOverride != null && !placeholderItemTitleOverride.isBlank()
|
||||||
? placeholderItemTitleOverride
|
? placeholderItemTitleOverride
|
||||||
: Component.translatable("playersync.item_placeholder_title").getString())
|
: Component.translatable("playersync.item_placeholder_title").getString())
|
||||||
.setStyle(Style.EMPTY.withColor(ChatFormatting.RED).withItalic(true))));
|
.setStyle(Style.EMPTY.withColor(ChatFormatting.RED).withItalic(true)));
|
||||||
|
|
||||||
ListTag loreList = new ListTag();
|
List<Component> loreList = new ArrayList<>();
|
||||||
String placeholderItemDetails = registryName.toString();
|
String placeholderItemDetails = registryName.toString();
|
||||||
|
|
||||||
// add a stack size if it is available
|
// add a stack size if it is available
|
||||||
|
|
@ -325,11 +328,11 @@ public class VanillaSync {
|
||||||
placeholderItemDetails = placeholderItemAmount + "x " + placeholderItemDetails;
|
placeholderItemDetails = placeholderItemAmount + "x " + placeholderItemDetails;
|
||||||
}
|
}
|
||||||
|
|
||||||
loreList.add(StringTag.valueOf(Component.Serializer.toJson(
|
loreList.add(
|
||||||
Component.literal(placeholderItemDetails)
|
Component.literal(placeholderItemDetails)
|
||||||
.setStyle(Style.EMPTY.withColor(ChatFormatting.GRAY).withItalic(false)))));
|
.setStyle(Style.EMPTY.withColor(ChatFormatting.GRAY).withItalic(false)));
|
||||||
// add newline
|
// add newline
|
||||||
loreList.add(StringTag.valueOf(Component.Serializer.toJson(Component.literal(""))));
|
loreList.add(Component.literal(""));
|
||||||
|
|
||||||
String placeholderItemDescriptionOverride = JdbcConfig.ITEM_PLACEHOLDER_DESCRIPTION_OVERRIDE.get();
|
String placeholderItemDescriptionOverride = JdbcConfig.ITEM_PLACEHOLDER_DESCRIPTION_OVERRIDE.get();
|
||||||
String placeholderItemDescriptionLines = placeholderItemDescriptionOverride != null && ! placeholderItemDescriptionOverride.isBlank()
|
String placeholderItemDescriptionLines = placeholderItemDescriptionOverride != null && ! placeholderItemDescriptionOverride.isBlank()
|
||||||
|
|
@ -337,11 +340,12 @@ public class VanillaSync {
|
||||||
: Component.translatable("playersync.item_placeholder_description").getString();
|
: Component.translatable("playersync.item_placeholder_description").getString();
|
||||||
|
|
||||||
for (String descriptionLine : placeholderItemDescriptionLines.split("\n")) {
|
for (String descriptionLine : placeholderItemDescriptionLines.split("\n")) {
|
||||||
loreList.add(StringTag.valueOf(Component.Serializer.toJson(
|
loreList.add(
|
||||||
Component.literal(descriptionLine)
|
Component.literal(descriptionLine)
|
||||||
.setStyle(Style.EMPTY.withColor(ChatFormatting.DARK_GRAY)))));
|
.setStyle(Style.EMPTY.withColor(ChatFormatting.DARK_GRAY)));
|
||||||
}
|
}
|
||||||
displayTag.put("Lore", loreList);
|
|
||||||
|
placeholder.set(DataComponents.LORE,new ItemLore(loreList));
|
||||||
|
|
||||||
return placeholder;
|
return placeholder;
|
||||||
}
|
}
|
||||||
|
|
@ -437,9 +441,9 @@ public class VanillaSync {
|
||||||
// Helper function to get the NBT string to be saved
|
// Helper function to get the NBT string to be saved
|
||||||
// If item is a placeholder, get original NBT; otherwise, get current NBT
|
// If item is a placeholder, get original NBT; otherwise, get current NBT
|
||||||
private static String getNbtForStorage(ItemStack itemStack) {
|
private static String getNbtForStorage(ItemStack itemStack) {
|
||||||
if (itemStack.is(Items.PAPER) && itemStack.hasTag() && itemStack.getTag().contains("playersync:original_item_nbt", Tag.TAG_STRING)) {
|
if (itemStack.is(Items.PAPER) && itemStack.getComponents().has(DataComponentTypes.ORIGINAL_ITEM_NBT.get())) {
|
||||||
// It's our placeholder, retrieve the original NBT string
|
// It's our placeholder, retrieve the original NBT string
|
||||||
return itemStack.getTag().getString("playersync:original_item_nbt");
|
return itemStack.getComponents().get(DataComponentTypes.ORIGINAL_ITEM_NBT.get());
|
||||||
} else {
|
} else {
|
||||||
// It's a normal item or empty, serialize its current NBT
|
// It's a normal item or empty, serialize its current NBT
|
||||||
return serialize(serializeNBT(itemStack).toString());
|
return serialize(serializeNBT(itemStack).toString());
|
||||||
|
|
@ -451,8 +455,9 @@ public class VanillaSync {
|
||||||
return new CompoundTag();
|
return new CompoundTag();
|
||||||
}
|
}
|
||||||
// Serialize the ItemStack to NBT
|
// Serialize the ItemStack to NBT
|
||||||
|
HolderLookup.Provider provider = ServerLifecycleHooks.getCurrentServer().registryAccess();
|
||||||
CompoundTag compoundTag = new CompoundTag();
|
CompoundTag compoundTag = new CompoundTag();
|
||||||
itemStack.save(compoundTag);
|
itemStack.save(provider);
|
||||||
return compoundTag;
|
return compoundTag;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -494,18 +499,18 @@ public class VanillaSync {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Effects
|
// Effects
|
||||||
Map<MobEffect, MobEffectInstance> effects = player.getActiveEffectsMap();
|
Map<Holder<MobEffect>, MobEffectInstance> effects = player.getActiveEffectsMap();
|
||||||
Map<Integer, String> effectMap = new HashMap<>();
|
Map<Integer, String> effectMap = new HashMap<>();
|
||||||
for (Map.Entry<MobEffect, MobEffectInstance> entry : effects.entrySet()) {
|
for (Map.Entry<Holder<MobEffect>, MobEffectInstance> entry : effects.entrySet()) {
|
||||||
CompoundTag effectTag = entry.getValue().save(new CompoundTag());
|
Tag effectTag = entry.getValue().save();
|
||||||
effectMap.put(BuiltInRegistries.MOB_EFFECT.getId(entry.getKey()), serialize(effectTag.toString()));
|
effectMap.put(BuiltInRegistries.MOB_EFFECT.getId(entry.getKey().value()), serialize(effectTag.toString()));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Advancements
|
// Advancements
|
||||||
File advancements = null;
|
File advancements = null;
|
||||||
byte[] advancementBytes = new byte[0];
|
byte[] advancementBytes = new byte[0];
|
||||||
if (JdbcConfig.SYNC_ADVANCEMENTS.get()) {
|
if (JdbcConfig.SYNC_ADVANCEMENTS.get()) {
|
||||||
File gameDir = Objects.requireNonNull(player.getServer()).getServerDirectory();
|
File gameDir = Objects.requireNonNull(player.getServer()).getServerDirectory().toFile();
|
||||||
final MinecraftServer server = ServerLifecycleHooks.getCurrentServer();
|
final MinecraftServer server = ServerLifecycleHooks.getCurrentServer();
|
||||||
if (server != null && server.isDedicatedServer() ) {
|
if (server != null && server.isDedicatedServer() ) {
|
||||||
PlayerSync.LOGGER.trace("Reading dedicated server advancements");
|
PlayerSync.LOGGER.trace("Reading dedicated server advancements");
|
||||||
|
|
@ -576,7 +581,7 @@ public class VanillaSync {
|
||||||
static int tick = 0;
|
static int tick = 0;
|
||||||
|
|
||||||
@SubscribeEvent
|
@SubscribeEvent
|
||||||
public static void onUpdate(TickEvent.LevelTickEvent event) throws SQLException {
|
public static void onUpdate(LevelTickEvent event) throws SQLException {
|
||||||
tick++;
|
tick++;
|
||||||
if (tick == 1800) {
|
if (tick == 1800) {
|
||||||
tick = 0;
|
tick = 0;
|
||||||
|
|
@ -592,37 +597,35 @@ public class VanillaSync {
|
||||||
|
|
||||||
//AutoSave
|
//AutoSave
|
||||||
@SubscribeEvent
|
@SubscribeEvent
|
||||||
public static void onServerTick(TickEvent.ServerTickEvent event) {
|
public static void onServerTick(ServerTickEvent.Post event) {
|
||||||
// Run at the end phase to avoid interfering with game logic
|
// Run at the end phase to avoid interfering with game logic
|
||||||
if (event.phase == TickEvent.Phase.END) {
|
autoSaveTickCounter++;
|
||||||
autoSaveTickCounter++;
|
if (autoSaveTickCounter >= AUTO_SAVE_INTERVAL_TICKS) {
|
||||||
if (autoSaveTickCounter >= AUTO_SAVE_INTERVAL_TICKS) {
|
autoSaveTickCounter = 0;
|
||||||
autoSaveTickCounter = 0;
|
// Retrieve the current server instance
|
||||||
// Retrieve the current server instance
|
MinecraftServer server = ServerLifecycleHooks.getCurrentServer();
|
||||||
MinecraftServer server = ServerLifecycleHooks.getCurrentServer();
|
if (server != null) {
|
||||||
if (server != null) {
|
// Iterate through all online players
|
||||||
// Iterate through all online players
|
for (ServerPlayer player : server.getPlayerList().getPlayers()) {
|
||||||
for (ServerPlayer player : server.getPlayerList().getPlayers()) {
|
executorService.submit(() -> {
|
||||||
executorService.submit(() -> {
|
try {
|
||||||
try {
|
// Call the same store method used in logout and file save events.
|
||||||
// Call the same store method used in logout and file save events.
|
store(player, false);
|
||||||
store(player, false);
|
} catch (Exception e) {
|
||||||
} catch (Exception e) {
|
PlayerSync.LOGGER.error("Error auto-saving player " + player.getUUID(), e);
|
||||||
PlayerSync.LOGGER.error("Error auto-saving player " + player.getUUID(), e);
|
}
|
||||||
}
|
});
|
||||||
});
|
executorService.submit(() -> {
|
||||||
executorService.submit(() -> {
|
try {
|
||||||
try {
|
new ModsSupport().StoreCurios(player, false);
|
||||||
new ModsSupport().StoreCurios(player, false);
|
} catch (SQLException e) {
|
||||||
} catch (SQLException e) {
|
PlayerSync.LOGGER.error("Error auto-saving Curios data for player " + player.getUUID(), e);
|
||||||
PlayerSync.LOGGER.error("Error auto-saving Curios data for player " + player.getUUID(), e);
|
}
|
||||||
}
|
});
|
||||||
});
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void setXpForPlayer(ServerPlayer serverPlayer, int databaseXp) {
|
private static void setXpForPlayer(ServerPlayer serverPlayer, int databaseXp) {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user