diff --git a/build.gradle b/build.gradle index 0c0669bf..50b9cab8 100644 --- a/build.gradle +++ b/build.gradle @@ -162,6 +162,10 @@ dependencies { testRuntimeOnly 'org.junit.jupiter:junit-jupiter-engine:5.9.2' } +test { + useJUnitPlatform() +} + def replaceProperties = [ mc_version: mc_version, mod_version: version ] processResources { diff --git a/src/main/java/thedarkcolour/exdeorum/blockentity/BarrelBlockEntity.java b/src/main/java/thedarkcolour/exdeorum/blockentity/BarrelBlockEntity.java index b7071cf5..c364df7a 100644 --- a/src/main/java/thedarkcolour/exdeorum/blockentity/BarrelBlockEntity.java +++ b/src/main/java/thedarkcolour/exdeorum/blockentity/BarrelBlockEntity.java @@ -274,7 +274,9 @@ public class BarrelBlockEntity extends EBlockEntity { if (recipe != null && this.tank.getFluidAmount() >= recipe.baseFluidAmount && itemFluid.getAmount() == 1000) { if (!level.isClientSide) { this.tank.drain(recipe.baseFluidAmount, IFluidHandler.FluidAction.EXECUTE); - setItem(new ItemStack(recipe.result)); + ItemStack result = new ItemStack(recipe.result); + result.setTag(recipe.getResultNbt()); + setItem(result); if (recipe.consumesAdditive) { itemFluidCap.drain(1000, IFluidHandler.FluidAction.EXECUTE); @@ -378,7 +380,9 @@ public class BarrelBlockEntity extends EBlockEntity { // Empty barrel this.tank.drain(recipe.fluidAmount, IFluidHandler.FluidAction.EXECUTE); // Replace fluid with result - setItem(new ItemStack(recipe.result)); + ItemStack result = new ItemStack(recipe.result); + result.setTag(recipe.getResultNbt()); + setItem(result); this.level.playSound(null, this.worldPosition, SoundEvents.AMBIENT_UNDERWATER_EXIT, SoundSource.BLOCKS, 0.8f, 0.8f); } // Mixing was successful, so return true diff --git a/src/main/java/thedarkcolour/exdeorum/blockentity/InfestedLeavesBlockEntity.java b/src/main/java/thedarkcolour/exdeorum/blockentity/InfestedLeavesBlockEntity.java index afc51ce0..32daa15b 100644 --- a/src/main/java/thedarkcolour/exdeorum/blockentity/InfestedLeavesBlockEntity.java +++ b/src/main/java/thedarkcolour/exdeorum/blockentity/InfestedLeavesBlockEntity.java @@ -41,10 +41,7 @@ public class InfestedLeavesBlockEntity extends EBlockEntity { public static final float PROGRESS_INTERVAL = 0.005f; public static final int SPREAD_INTERVAL = 40; - public static final ModelProperty MIMIC_PROPERTY = new ModelProperty<>(); - // A percentage of how much this leaf is infested - // todo change this to a short between 0 and 16000 private float progress; // A timer that determines when this block should try to spread private int spreadTimer; @@ -66,24 +63,24 @@ public class InfestedLeavesBlockEntity extends EBlockEntity { } // Attempt to convert a leaf block within 1 block radius around this block - private void trySpread() { + private void trySpread(Level level) { // Get random offset - int x = this.level.random.nextInt(3) - 1; - int y = this.level.random.nextInt(3) - 1; - int z = this.level.random.nextInt(3) - 1; + int x = level.random.nextInt(3) - 1; + int y = level.random.nextInt(3) - 1; + int z = level.random.nextInt(3) - 1; // Get the block in the world BlockPos targetPos = getBlockPos().offset(x, y, z); - BlockState state = this.level.getBlockState(targetPos); + BlockState state = level.getBlockState(targetPos); // DO NOT SPREAD TO ALREADY INFESTED LEAVES if (state.is(BlockTags.LEAVES) && state.getBlock() != EBlocks.INFESTED_LEAVES.get()) { // Spread and keep distance/persistent properties - this.level.setBlock(targetPos, EBlocks.INFESTED_LEAVES.get().defaultBlockState() + level.setBlock(targetPos, EBlocks.INFESTED_LEAVES.get().defaultBlockState() .setValue(LeavesBlock.DISTANCE, state.getValue(LeavesBlock.DISTANCE)) .setValue(LeavesBlock.PERSISTENT, state.getValue(LeavesBlock.PERSISTENT)), 2); - var te = this.level.getBlockEntity(targetPos); + var te = level.getBlockEntity(targetPos); // Set mimic state of other block if (te instanceof InfestedLeavesBlockEntity leaves) { @@ -131,11 +128,6 @@ public class InfestedLeavesBlockEntity extends EBlockEntity { this.mimic = mimic; } - @Override - public @NotNull ModelData getModelData() { - return ModelData.builder().with(MIMIC_PROPERTY, this.mimic).build(); - } - public static class Ticker implements BlockEntityTicker { @Override public void tick(Level level, BlockPos pos, BlockState state, InfestedLeavesBlockEntity leaves) { @@ -154,7 +146,7 @@ public class InfestedLeavesBlockEntity extends EBlockEntity { // Attempt to spread and reset the timer if (leaves.spreadTimer >= SPREAD_INTERVAL) { - leaves.trySpread(); + leaves.trySpread(level); leaves.spreadTimer = level.random.nextInt(10); } } diff --git a/src/main/java/thedarkcolour/exdeorum/blockentity/MechanicalHammerBlockEntity.java b/src/main/java/thedarkcolour/exdeorum/blockentity/MechanicalHammerBlockEntity.java index eb7b10c6..03402a6b 100644 --- a/src/main/java/thedarkcolour/exdeorum/blockentity/MechanicalHammerBlockEntity.java +++ b/src/main/java/thedarkcolour/exdeorum/blockentity/MechanicalHammerBlockEntity.java @@ -43,6 +43,8 @@ import thedarkcolour.exdeorum.recipe.hammer.HammerRecipe; import thedarkcolour.exdeorum.registry.EBlockEntities; import thedarkcolour.exdeorum.tag.EItemTags; +import java.util.Objects; + public class MechanicalHammerBlockEntity extends AbstractMachineBlockEntity { private static final Component TITLE = Component.translatable(TranslationKeys.MECHANICAL_HAMMER_SCREEN_TITLE); private static final int INPUT_SLOT = 0; @@ -127,7 +129,7 @@ public class MechanicalHammerBlockEntity extends AbstractMachineBlockEntity implements IRecipeCategory { public void setRecipe(IRecipeLayoutBuilder builder, BarrelMixingRecipe recipe, IFocusGroup focuses) { builder.addSlot(RecipeIngredientRole.INPUT, 1, 1).addFluidStack(recipe.fluid, recipe.fluidAmount).setFluidRenderer(1000, false, 16, 16); builder.addSlot(RecipeIngredientRole.INPUT, 33, 1).addIngredients(recipe.getIngredient()); - builder.addSlot(RecipeIngredientRole.OUTPUT, 79, 1).addItemStack(new ItemStack(recipe.result)); + ItemStack result = new ItemStack(recipe.result); + result.setTag(recipe.getResultNbt()); + builder.addSlot(RecipeIngredientRole.OUTPUT, 79, 1).addItemStack(result); } @Override @@ -113,7 +115,9 @@ public abstract class BarrelMixingCategory implements IRecipeCategory { if (recipe.consumesAdditive) { additiveSlot.addTooltipCallback((view, tooltip) -> tooltip.add(CONTENTS_ARE_CONSUMED_TOOLTIP)); } - builder.addSlot(RecipeIngredientRole.OUTPUT, 79, 1).addItemStack(new ItemStack(recipe.result)); + ItemStack result = new ItemStack(recipe.result); + result.setTag(recipe.getResultNbt()); + builder.addSlot(RecipeIngredientRole.OUTPUT, 79, 1).addItemStack(result); } @Override diff --git a/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookCategory.java b/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookCategory.java index eabaa1db..b804e8cf 100644 --- a/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookCategory.java +++ b/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookCategory.java @@ -100,7 +100,9 @@ public class CrookCategory implements IRecipeCategory { @Override public void setRecipe(IRecipeLayoutBuilder builder, CrookJeiRecipe recipe, IFocusGroup focuses) { recipe.addIngredients(builder); - builder.addSlot(RecipeIngredientRole.OUTPUT, 80, 18).addItemStack(new ItemStack(recipe.result)).addTooltipCallback((recipeSlotView, tooltip) -> { + ItemStack result = new ItemStack(recipe.result, 1); + result.setTag(recipe.getResultNbt()); + builder.addSlot(RecipeIngredientRole.OUTPUT, 80, 18).addItemStack(result).addTooltipCallback((recipeSlotView, tooltip) -> { tooltip.add(ClientJeiUtil.formatChance(recipe.chance)); }); } diff --git a/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookJeiRecipe.java b/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookJeiRecipe.java index d4b98a20..ae8c55ee 100644 --- a/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookJeiRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/compat/jei/CrookJeiRecipe.java @@ -24,6 +24,7 @@ import mezz.jei.api.gui.builder.IRecipeLayoutBuilder; import mezz.jei.api.recipe.RecipeIngredientRole; import net.minecraft.ChatFormatting; import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.chat.Component; import net.minecraft.tags.TagKey; import net.minecraft.world.item.Item; @@ -43,11 +44,14 @@ import java.util.List; public sealed abstract class CrookJeiRecipe { public final List states; public Item result; + @Nullable + private final CompoundTag resultNbt; public float chance; - public CrookJeiRecipe(List states, Item result, float chance) { + public CrookJeiRecipe(List states, Item result, @Nullable CompoundTag resultNbt, float chance) { this.states = states; this.result = result; + this.resultNbt = resultNbt; this.chance = chance; } @@ -55,30 +59,36 @@ public sealed abstract class CrookJeiRecipe { static CrookJeiRecipe create(CrookRecipe recipe) { if (recipe.blockPredicate() instanceof BlockPredicate.BlockStatePredicate state) { - return new StatesRecipe(state, state.possibleStates().filter(blockState -> !blockState.hasProperty(BlockStateProperties.WATERLOGGED) || !blockState.getValue(BlockStateProperties.WATERLOGGED)).toList(), recipe.result(), recipe.chance()); + return new StatesRecipe(state, state.possibleStates().filter(blockState -> !blockState.hasProperty(BlockStateProperties.WATERLOGGED) || !blockState.getValue(BlockStateProperties.WATERLOGGED)).toList(), recipe.result(), recipe.resultNbt(), recipe.chance()); } else if (recipe.blockPredicate() instanceof BlockPredicate.SingleBlockPredicate block) { - return new BlockRecipe(block.block(), recipe.result(), recipe.chance()); + return new BlockRecipe(block.block(), recipe.result(), recipe.resultNbt(), recipe.chance()); } else if (recipe.blockPredicate() instanceof BlockPredicate.TagPredicate tag) { var list = new ArrayList(); + //noinspection deprecation for (var holder : BuiltInRegistries.BLOCK.getTagOrEmpty(tag.tag())) { if (holder.isBound()) { list.add(holder.value().defaultBlockState()); } } - return new TagRecipe(tag.tag(), List.copyOf(list), recipe.result(), recipe.chance()); + return new TagRecipe(tag.tag(), List.copyOf(list), recipe.result(), recipe.resultNbt(), recipe.chance()); } throw new IllegalArgumentException("Invalid crook recipe?? -> " + recipe); } + @Nullable + public CompoundTag getResultNbt() { + return this.resultNbt == null ? null : this.resultNbt.copy(); + } + sealed static class StatesRecipe extends CrookJeiRecipe { private final List itemIngredients; public final List requirements; - StatesRecipe(@Nullable BlockPredicate.BlockStatePredicate predicate, List states, Item result, float chance) { - super(states, result, chance); + StatesRecipe(@Nullable BlockPredicate.BlockStatePredicate predicate, List states, Item result, @Nullable CompoundTag resultNbt, float chance) { + super(states, result, resultNbt, chance); ImmutableList.Builder itemIngredients = ImmutableList.builder(); var blocks = new HashSet(); @@ -120,8 +130,8 @@ public sealed abstract class CrookJeiRecipe { static final class TagRecipe extends StatesRecipe { public final TagKey tag; - public TagRecipe(TagKey tag, List states, Item result, float chance) { - super(null, states, result, chance); + public TagRecipe(TagKey tag, List states, Item result, @Nullable CompoundTag resultNbt, float chance) { + super(null, states, result, resultNbt, chance); this.tag = tag; } } @@ -129,8 +139,8 @@ public sealed abstract class CrookJeiRecipe { static final class BlockRecipe extends CrookJeiRecipe { private final ItemStack itemIngredient; - BlockRecipe(Block block, Item result, float chance) { - super(List.of(block.defaultBlockState()), result, chance); + BlockRecipe(Block block, Item result, @Nullable CompoundTag resultNbt, float chance) { + super(List.of(block.defaultBlockState()), result, resultNbt, chance); var item = block.asItem(); if (item == Items.AIR) { diff --git a/src/main/java/thedarkcolour/exdeorum/compat/jei/HammerCategory.java b/src/main/java/thedarkcolour/exdeorum/compat/jei/HammerCategory.java index 7c8ada41..e904b5b9 100644 --- a/src/main/java/thedarkcolour/exdeorum/compat/jei/HammerCategory.java +++ b/src/main/java/thedarkcolour/exdeorum/compat/jei/HammerCategory.java @@ -26,9 +26,7 @@ import net.minecraft.network.chat.Component; import net.minecraft.world.item.Item; import net.minecraft.world.item.ItemStack; import net.minecraft.world.level.storage.loot.providers.number.ConstantValue; -import thedarkcolour.exdeorum.data.TranslationKeys; import thedarkcolour.exdeorum.recipe.hammer.HammerRecipe; -import thedarkcolour.exdeorum.registry.EItems; import java.util.function.Supplier; @@ -53,11 +51,14 @@ class HammerCategory extends OneToOneCategory { @Override protected void addOutput(IRecipeSlotBuilder slot, HammerRecipe recipe) { + ItemStack result; if (recipe.resultAmount instanceof ConstantValue constant) { - slot.addItemStack(new ItemStack(recipe.result, (int) constant.value)); + result = new ItemStack(recipe.result, (int) constant.value); } else { - slot.addItemStack(new ItemStack(recipe.result)); - SieveCategory.addTooltips(slot, false, recipe.resultAmount); + result = new ItemStack(recipe.result, 1); } + SieveCategory.addTooltips(slot, false, recipe.resultAmount); + result.setTag(recipe.getResultNbt()); + slot.addItemStack(result); } } diff --git a/src/main/java/thedarkcolour/exdeorum/loot/CrookLootModifier.java b/src/main/java/thedarkcolour/exdeorum/loot/CrookLootModifier.java index 4cdbb809..d4cd64e4 100644 --- a/src/main/java/thedarkcolour/exdeorum/loot/CrookLootModifier.java +++ b/src/main/java/thedarkcolour/exdeorum/loot/CrookLootModifier.java @@ -33,7 +33,6 @@ import net.minecraft.world.level.storage.loot.parameters.LootContextParams; import net.minecraft.world.level.storage.loot.predicates.LootItemCondition; import net.minecraftforge.common.loot.IGlobalLootModifier; import net.minecraftforge.common.loot.LootModifier; -import org.jetbrains.annotations.NotNull; import thedarkcolour.exdeorum.recipe.RecipeUtil; import thedarkcolour.exdeorum.recipe.crook.CrookRecipe; @@ -47,7 +46,7 @@ public class CrookLootModifier extends LootModifier { } @Override - protected @NotNull ObjectArrayList doApply(ObjectArrayList generatedLoot, LootContext context) { + protected ObjectArrayList doApply(ObjectArrayList generatedLoot, LootContext context) { var state = context.getParamOrNull(LootContextParams.BLOCK_STATE); var stack = context.getParamOrNull(LootContextParams.TOOL); @@ -61,7 +60,9 @@ public class CrookLootModifier extends LootModifier { for (CrookRecipe recipe : RecipeUtil.getCrookRecipes(state)) { for (int i = 0; i < rolls; i++) { if (rand.nextFloat() < recipe.chance()) { - generatedLoot.add(new ItemStack(recipe.result())); + ItemStack result = new ItemStack(recipe.result(), 1); + result.setTag(recipe.getResultNbt()); + generatedLoot.add(result); } } } diff --git a/src/main/java/thedarkcolour/exdeorum/loot/HammerLootModifier.java b/src/main/java/thedarkcolour/exdeorum/loot/HammerLootModifier.java index f78b0081..3f290bef 100644 --- a/src/main/java/thedarkcolour/exdeorum/loot/HammerLootModifier.java +++ b/src/main/java/thedarkcolour/exdeorum/loot/HammerLootModifier.java @@ -62,7 +62,9 @@ public class HammerLootModifier extends LootModifier { } if (resultAmount > 0) { - newLoot.add(new ItemStack(recipe.result, resultAmount)); + ItemStack result = new ItemStack(recipe.result, resultAmount); + result.setTag(recipe.getResultNbt()); + newLoot.add(result); } return newLoot; } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/ProbabilityRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/ProbabilityRecipe.java index 8bfe0bd4..eadd256b 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/ProbabilityRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/ProbabilityRecipe.java @@ -19,24 +19,42 @@ package thedarkcolour.exdeorum.recipe; import net.minecraft.core.RegistryAccess; +import net.minecraft.nbt.CompoundTag; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.item.Item; import net.minecraft.world.item.ItemStack; import net.minecraft.world.item.crafting.Ingredient; import net.minecraft.world.level.storage.loot.providers.number.NumberProvider; +import org.jetbrains.annotations.Nullable; public abstract class ProbabilityRecipe extends SingleIngredientRecipe { public final Item result; public final NumberProvider resultAmount; + @Nullable + protected final CompoundTag resultNbt; - public ProbabilityRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount) { + public ProbabilityRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt) { super(id, ingredient); this.result = result; this.resultAmount = resultAmount; + this.resultNbt = resultNbt; + } + + @Nullable + public CompoundTag getResultNbt() { + return this.resultNbt == null ? null : this.resultNbt.copy(); + } + + // Do not use in ItemStack, compound tags are mutable and new copies should be made per stack + @Nullable + public CompoundTag getRawResultNbt() { + return this.resultNbt; } @Override public ItemStack getResultItem(RegistryAccess access) { - return new ItemStack(this.result); + ItemStack result = new ItemStack(this.result, 1); + result.setTag(getResultNbt()); + return result; } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/RecipeUtil.java b/src/main/java/thedarkcolour/exdeorum/recipe/RecipeUtil.java index ae6c55db..30f56a4c 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/RecipeUtil.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/RecipeUtil.java @@ -28,6 +28,7 @@ import it.unimi.dsi.fastutil.objects.ObjectArrayList; import it.unimi.dsi.fastutil.objects.ObjectSet; import net.minecraft.commands.arguments.blocks.BlockStateParser; import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.resources.ResourceLocation; import net.minecraft.server.level.ServerLevel; @@ -501,4 +502,9 @@ public final class RecipeUtil { public static String writeItemJson(Item result) { return BuiltInRegistries.ITEM.getKey(result).toString(); } + + @Nullable + public static CompoundTag readNbtTag(JsonObject json, String key) { + return json.has(key) ? CraftingHelper.getNBT(json.get(key)) : null; + } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelFluidMixingRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelFluidMixingRecipe.java index f56cc460..0c0da806 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelFluidMixingRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelFluidMixingRecipe.java @@ -20,6 +20,7 @@ package thedarkcolour.exdeorum.recipe.barrel; import com.google.gson.JsonObject; import net.minecraft.core.RegistryAccess; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.resources.ResourceLocation; import net.minecraft.util.GsonHelper; @@ -48,14 +49,17 @@ public class BarrelFluidMixingRecipe implements Recipe { public final int baseFluidAmount; public final Fluid additiveFluid; public final Item result; + @Nullable + protected final CompoundTag resultNbt; public final boolean consumesAdditive; - public BarrelFluidMixingRecipe(ResourceLocation id, Fluid baseFluid, int baseFluidAmount, Fluid additiveFluid, Item result, boolean consumesAdditive) { + public BarrelFluidMixingRecipe(ResourceLocation id, Fluid baseFluid, int baseFluidAmount, Fluid additiveFluid, Item result, @Nullable CompoundTag resultNbt, boolean consumesAdditive) { this.id = id; this.baseFluid = baseFluid; this.baseFluidAmount = baseFluidAmount; this.additiveFluid = additiveFluid; this.result = result; + this.resultNbt = resultNbt; this.consumesAdditive = consumesAdditive; } @@ -94,6 +98,11 @@ public class BarrelFluidMixingRecipe implements Recipe { return ERecipeTypes.BARREL_FLUID_MIXING.get(); } + @Nullable + public CompoundTag getResultNbt() { + return this.resultNbt == null ? null : this.resultNbt.copy(); + } + public static class Serializer implements RecipeSerializer { @Override public BarrelFluidMixingRecipe fromJson(ResourceLocation id, JsonObject json) { @@ -101,9 +110,10 @@ public class BarrelFluidMixingRecipe implements Recipe { int baseFluidAmount = GsonHelper.getAsInt(json, "base_fluid_amount"); Fluid additiveFluid = RecipeUtil.readFluid(json, "additive_fluid"); Item result = RecipeUtil.readItem(json, "result"); + CompoundTag resultNbt = RecipeUtil.readNbtTag(json, "result_nbt"); boolean consumesAdditive = GsonHelper.getAsBoolean(json, "consumes_additive"); - return new BarrelFluidMixingRecipe(id, baseFluid, baseFluidAmount, additiveFluid, result, consumesAdditive); + return new BarrelFluidMixingRecipe(id, baseFluid, baseFluidAmount, additiveFluid, result, resultNbt, consumesAdditive); } @Override @@ -112,6 +122,7 @@ public class BarrelFluidMixingRecipe implements Recipe { buffer.writeVarInt(recipe.baseFluidAmount); buffer.writeRegistryId(ForgeRegistries.FLUIDS, recipe.additiveFluid); buffer.writeRegistryId(ForgeRegistries.ITEMS, recipe.result); + buffer.writeNbt(recipe.resultNbt); buffer.writeBoolean(recipe.consumesAdditive); } @@ -121,9 +132,10 @@ public class BarrelFluidMixingRecipe implements Recipe { int baseFluidAmount = buffer.readVarInt(); Fluid additiveFluid = buffer.readRegistryId(); Item result = buffer.readRegistryId(); + CompoundTag resultNbt = buffer.readNbt(); boolean consumesAdditive = buffer.readBoolean(); - return new BarrelFluidMixingRecipe(id, baseFluid, baseFluidAmount, additiveFluid, result, consumesAdditive); + return new BarrelFluidMixingRecipe(id, baseFluid, baseFluidAmount, additiveFluid, result, resultNbt, consumesAdditive); } } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelMixingRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelMixingRecipe.java index 4409ba1c..fbf5b73f 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelMixingRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/barrel/BarrelMixingRecipe.java @@ -20,6 +20,7 @@ package thedarkcolour.exdeorum.recipe.barrel; import com.google.gson.JsonObject; import net.minecraft.core.RegistryAccess; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.resources.ResourceLocation; import net.minecraft.util.GsonHelper; @@ -43,12 +44,20 @@ public class BarrelMixingRecipe extends SingleIngredientRecipe { public final Fluid fluid; public final int fluidAmount; public final Item result; + @Nullable + protected final CompoundTag resultNbt; - public BarrelMixingRecipe(ResourceLocation id, Ingredient ingredient, Fluid fluid, int fluidAmount, Item result) { + public BarrelMixingRecipe(ResourceLocation id, Ingredient ingredient, Fluid fluid, int fluidAmount, Item result, @Nullable CompoundTag resultNbt) { super(id, ingredient); this.fluid = fluid; this.fluidAmount = fluidAmount; this.result = result; + this.resultNbt = resultNbt; + } + + @Nullable + public CompoundTag getResultNbt() { + return this.resultNbt == null ? null : this.resultNbt.copy(); } // Do not use @@ -84,8 +93,9 @@ public class BarrelMixingRecipe extends SingleIngredientRecipe { Fluid fluid = RecipeUtil.readFluid(json, "fluid"); int fluidAmount = GsonHelper.getAsInt(json, "fluid_amount"); Item result = RecipeUtil.readItem(json, "result"); + CompoundTag resultNbt = RecipeUtil.readNbtTag(json, "result_nbt"); - return new BarrelMixingRecipe(id, ingredient, fluid, fluidAmount, result); + return new BarrelMixingRecipe(id, ingredient, fluid, fluidAmount, result, resultNbt); } @Override @@ -94,6 +104,7 @@ public class BarrelMixingRecipe extends SingleIngredientRecipe { buffer.writeRegistryId(ForgeRegistries.FLUIDS, recipe.fluid); buffer.writeVarInt(recipe.fluidAmount); buffer.writeRegistryId(ForgeRegistries.ITEMS, recipe.result); + buffer.writeNbt(recipe.resultNbt); } @Override @@ -102,8 +113,9 @@ public class BarrelMixingRecipe extends SingleIngredientRecipe { Fluid fluid = buffer.readRegistryId(); int fluidAmount = buffer.readVarInt(); Item result = buffer.readRegistryId(); + CompoundTag resultNbt = buffer.readNbt(); - return new BarrelMixingRecipe(id, ingredient, fluid, fluidAmount, result); + return new BarrelMixingRecipe(id, ingredient, fluid, fluidAmount, result, resultNbt); } } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/crook/CrookRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/crook/CrookRecipe.java index 0ffb2a95..bed0fd99 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/crook/CrookRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/crook/CrookRecipe.java @@ -21,22 +21,30 @@ package thedarkcolour.exdeorum.recipe.crook; import com.google.gson.JsonObject; import net.minecraft.core.RegistryAccess; import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.Container; import net.minecraft.world.item.Item; import net.minecraft.world.item.ItemStack; -import net.minecraft.world.item.Items; import net.minecraft.world.item.crafting.Recipe; import net.minecraft.world.item.crafting.RecipeSerializer; import net.minecraft.world.item.crafting.RecipeType; import net.minecraft.world.level.Level; +import org.jetbrains.annotations.Nullable; import thedarkcolour.exdeorum.recipe.BlockPredicate; import thedarkcolour.exdeorum.recipe.RecipeUtil; import thedarkcolour.exdeorum.registry.ERecipeSerializers; import thedarkcolour.exdeorum.registry.ERecipeTypes; -public record CrookRecipe(ResourceLocation id, BlockPredicate blockPredicate, Item result, float chance) implements Recipe { +import java.util.Objects; + +public record CrookRecipe(ResourceLocation id, BlockPredicate blockPredicate, Item result, @Nullable CompoundTag resultNbt, float chance) implements Recipe { + @Nullable + public CompoundTag getResultNbt() { + return this.resultNbt == null ? null : this.resultNbt.copy(); + } + @Override public boolean matches(Container pContainer, Level pLevel) { return false; @@ -54,7 +62,9 @@ public record CrookRecipe(ResourceLocation id, BlockPredicate blockPredicate, It @Override public ItemStack getResultItem(RegistryAccess pRegistryAccess) { - return new ItemStack(this.result); + ItemStack result = new ItemStack(this.result, 1); + result.setTag(getResultNbt()); + return result; } @Override @@ -72,38 +82,37 @@ public record CrookRecipe(ResourceLocation id, BlockPredicate blockPredicate, It return ERecipeTypes.CROOK.get(); } - @SuppressWarnings("deprecation") public static class Serializer implements RecipeSerializer { @Override public CrookRecipe fromJson(ResourceLocation id, JsonObject json) { - BlockPredicate blockPredicate = RecipeUtil.readBlockPredicate(id, json, "block_predicate"); - if (blockPredicate == null) return null; + BlockPredicate blockPredicate = Objects.requireNonNull(RecipeUtil.readBlockPredicate(id, json, "block_predicate")); Item result = RecipeUtil.readItem(json, "result"); + CompoundTag resultNbt = RecipeUtil.readNbtTag(json, "result_nbt"); float chance = json.get("chance").getAsFloat(); - - return new CrookRecipe(id, blockPredicate, result, chance); + return new CrookRecipe(id, blockPredicate, result, resultNbt, chance); } @Override + @SuppressWarnings("deprecation") public CrookRecipe fromNetwork(ResourceLocation id, FriendlyByteBuf buffer) { BlockPredicate blockPredicate = RecipeUtil.readBlockPredicateNetwork(id, buffer); if (blockPredicate == null) return null; - Item result = buffer.readById(BuiltInRegistries.ITEM); - if (result == null || result == Items.AIR) { - return null; - } + Item result = Objects.requireNonNull(buffer.readById(BuiltInRegistries.ITEM)); + CompoundTag resultNbt = buffer.readNbt(); float chance = buffer.readFloat(); - return new CrookRecipe(id, blockPredicate, result, chance); + return new CrookRecipe(id, blockPredicate, result, resultNbt, chance); } @Override + @SuppressWarnings("deprecation") public void toNetwork(FriendlyByteBuf buffer, CrookRecipe recipe) { recipe.blockPredicate.toNetwork(buffer); buffer.writeId(BuiltInRegistries.ITEM, recipe.result); + buffer.writeNbt(recipe.resultNbt); buffer.writeFloat(recipe.chance); } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/hammer/CompressedHammerRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/hammer/CompressedHammerRecipe.java index 2b697f4a..5f596130 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/hammer/CompressedHammerRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/hammer/CompressedHammerRecipe.java @@ -18,18 +18,21 @@ package thedarkcolour.exdeorum.recipe.hammer; +import net.minecraft.nbt.CompoundTag; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.item.Item; import net.minecraft.world.item.crafting.Ingredient; import net.minecraft.world.item.crafting.RecipeSerializer; import net.minecraft.world.item.crafting.RecipeType; import net.minecraft.world.level.storage.loot.providers.number.NumberProvider; +import org.jetbrains.annotations.Nullable; import thedarkcolour.exdeorum.registry.ERecipeSerializers; import thedarkcolour.exdeorum.registry.ERecipeTypes; public class CompressedHammerRecipe extends HammerRecipe { - public CompressedHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount) { - super(id, ingredient, result, resultAmount); + + public CompressedHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt) { + super(id, ingredient, result, resultAmount, resultNbt); } @Override @@ -44,8 +47,8 @@ public class CompressedHammerRecipe extends HammerRecipe { public static class Serializer extends HammerRecipe.AbstractSerializer { @Override - protected CompressedHammerRecipe createHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount) { - return new CompressedHammerRecipe(id, ingredient, result, resultAmount); + protected CompressedHammerRecipe createHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt) { + return new CompressedHammerRecipe(id, ingredient, result, resultAmount, resultNbt); } } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/hammer/HammerRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/hammer/HammerRecipe.java index 1c981c1b..529bedee 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/hammer/HammerRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/hammer/HammerRecipe.java @@ -20,6 +20,7 @@ package thedarkcolour.exdeorum.recipe.hammer; import com.google.gson.JsonObject; import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.item.Item; @@ -27,16 +28,25 @@ import net.minecraft.world.item.crafting.Ingredient; import net.minecraft.world.item.crafting.RecipeSerializer; import net.minecraft.world.item.crafting.RecipeType; import net.minecraft.world.level.storage.loot.providers.number.NumberProvider; +import org.jetbrains.annotations.Nullable; import thedarkcolour.exdeorum.recipe.ProbabilityRecipe; import thedarkcolour.exdeorum.recipe.RecipeUtil; +import thedarkcolour.exdeorum.recipe.sieve.SieveRecipe; import thedarkcolour.exdeorum.registry.ERecipeSerializers; import thedarkcolour.exdeorum.registry.ERecipeTypes; import java.util.Objects; public class HammerRecipe extends ProbabilityRecipe { - public HammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount) { - super(id, ingredient, result, resultAmount); + public HammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt) { + super(id, ingredient, result, resultAmount, resultNbt); + } + + public static boolean areEqual(HammerRecipe a, HammerRecipe b) { + if (a.getClass() != b.getClass()) return false; + return RecipeUtil.areIngredientsEqual(a.ingredient, b.ingredient) + && Objects.equals(a.result, b.result) + && Objects.equals(a.resultNbt, b.resultNbt); } @Override @@ -50,14 +60,16 @@ public class HammerRecipe extends ProbabilityRecipe { } public static abstract class AbstractSerializer implements RecipeSerializer { - protected abstract T createHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount); + protected abstract T createHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt); @Override public T fromJson(ResourceLocation name, JsonObject json) { Ingredient ingredient = RecipeUtil.readIngredient(json, "ingredient"); Item result = RecipeUtil.readItem(json, "result"); NumberProvider resultAmount = RecipeUtil.readNumberProvider(json, "result_amount"); - return createHammerRecipe(name, ingredient, result, resultAmount); + CompoundTag resultNbt = RecipeUtil.readNbtTag(json, "result_nbt"); + + return createHammerRecipe(name, ingredient, result, resultAmount, resultNbt); } @Override @@ -66,7 +78,8 @@ public class HammerRecipe extends ProbabilityRecipe { Ingredient ingredient = Ingredient.fromNetwork(buffer); Item result = Objects.requireNonNull(buffer.readById(BuiltInRegistries.ITEM)); NumberProvider resultAmount = RecipeUtil.fromNetworkNumberProvider(buffer); - return createHammerRecipe(name, ingredient, result, resultAmount); + CompoundTag resultNbt = buffer.readNbt(); + return createHammerRecipe(name, ingredient, result, resultAmount, resultNbt); } @Override @@ -75,13 +88,14 @@ public class HammerRecipe extends ProbabilityRecipe { recipe.getIngredient().toNetwork(buffer); buffer.writeId(BuiltInRegistries.ITEM, recipe.result); RecipeUtil.toNetworkNumberProvider(buffer, recipe.resultAmount); + buffer.writeNbt(recipe.resultNbt); } } public static class Serializer extends AbstractSerializer { @Override - protected HammerRecipe createHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount) { - return new HammerRecipe(id, ingredient, result, resultAmount); + protected HammerRecipe createHammerRecipe(ResourceLocation id, Ingredient ingredient, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt) { + return new HammerRecipe(id, ingredient, result, resultAmount, resultNbt); } } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/sieve/CompressedSieveRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/sieve/CompressedSieveRecipe.java index 0b6b7c67..67a0f06d 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/sieve/CompressedSieveRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/sieve/CompressedSieveRecipe.java @@ -18,18 +18,20 @@ package thedarkcolour.exdeorum.recipe.sieve; +import net.minecraft.nbt.CompoundTag; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.item.Item; import net.minecraft.world.item.crafting.Ingredient; import net.minecraft.world.item.crafting.RecipeSerializer; import net.minecraft.world.item.crafting.RecipeType; import net.minecraft.world.level.storage.loot.providers.number.NumberProvider; +import org.jetbrains.annotations.Nullable; import thedarkcolour.exdeorum.registry.ERecipeSerializers; import thedarkcolour.exdeorum.registry.ERecipeTypes; public class CompressedSieveRecipe extends SieveRecipe { - public CompressedSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, boolean byHandOnly) { - super(id, ingredient, mesh, result, resultAmount, byHandOnly); + public CompressedSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt, boolean byHandOnly) { + super(id, ingredient, mesh, result, resultAmount, resultNbt, byHandOnly); } @Override @@ -44,8 +46,8 @@ public class CompressedSieveRecipe extends SieveRecipe { public static class Serializer extends SieveRecipe.AbstractSerializer { @Override - protected CompressedSieveRecipe createSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, boolean byHandOnly) { - return new CompressedSieveRecipe(id, ingredient, mesh, result, resultAmount, byHandOnly); + protected CompressedSieveRecipe createSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt, boolean byHandOnly) { + return new CompressedSieveRecipe(id, ingredient, mesh, result, resultAmount, resultNbt, byHandOnly); } } } diff --git a/src/main/java/thedarkcolour/exdeorum/recipe/sieve/SieveRecipe.java b/src/main/java/thedarkcolour/exdeorum/recipe/sieve/SieveRecipe.java index a701fb50..8fde348a 100644 --- a/src/main/java/thedarkcolour/exdeorum/recipe/sieve/SieveRecipe.java +++ b/src/main/java/thedarkcolour/exdeorum/recipe/sieve/SieveRecipe.java @@ -22,6 +22,7 @@ import com.google.gson.JsonObject; import com.google.gson.JsonSyntaxException; import net.minecraft.core.registries.BuiltInRegistries; import net.minecraft.core.registries.Registries; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.resources.ResourceLocation; import net.minecraft.tags.TagKey; @@ -46,8 +47,8 @@ public class SieveRecipe extends ProbabilityRecipe { public final Item mesh; public final boolean byHandOnly; - public SieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, boolean byHandOnly) { - super(id, ingredient, result, resultAmount); + public SieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt, boolean byHandOnly) { + super(id, ingredient, result, resultAmount, resultNbt); this.mesh = mesh; this.byHandOnly = byHandOnly; @@ -63,8 +64,17 @@ public class SieveRecipe extends ProbabilityRecipe { return ERecipeTypes.SIEVE.get(); } + public static boolean areEqual(SieveRecipe a, SieveRecipe b) { + if (a.getClass() != b.getClass()) return false; + return a.byHandOnly == b.byHandOnly + && Objects.equals(a.mesh, b.mesh) + && RecipeUtil.areIngredientsEqual(a.ingredient, b.ingredient) + && Objects.equals(a.result, b.result) + && Objects.equals(a.resultNbt, b.resultNbt); + } + public static abstract class AbstractSerializer implements RecipeSerializer { - protected abstract T createSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, boolean byHandOnly); + protected abstract T createSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt, boolean byHandOnly); @Override public T fromJson(ResourceLocation id, JsonObject json) { @@ -87,18 +97,21 @@ public class SieveRecipe extends ProbabilityRecipe { } NumberProvider resultAmount = RecipeUtil.readNumberProvider(json, "result_amount"); + CompoundTag resultNbt = RecipeUtil.readNbtTag(json, "result_nbt"); boolean byHandOnly = json.has("by_hand_only") && json.get("by_hand_only").getAsBoolean(); - return createSieveRecipe(id, ingredient, mesh, result, resultAmount, byHandOnly); + return createSieveRecipe(id, ingredient, mesh, result, resultAmount, resultNbt, byHandOnly); } @SuppressWarnings("deprecation") @Override - public @Nullable T fromNetwork(ResourceLocation id, FriendlyByteBuf buffer) { + public T fromNetwork(ResourceLocation id, FriendlyByteBuf buffer) { Ingredient ingredient = Ingredient.fromNetwork(buffer); Item mesh = Objects.requireNonNull(buffer.readById(BuiltInRegistries.ITEM)); Item result = Objects.requireNonNull(buffer.readById(BuiltInRegistries.ITEM)); NumberProvider resultAmount = RecipeUtil.fromNetworkNumberProvider(buffer); - return createSieveRecipe(id, ingredient, mesh, result, resultAmount, buffer.readBoolean()); + CompoundTag resultNbt = buffer.readNbt(); + boolean byHandOnly = buffer.readBoolean(); + return createSieveRecipe(id, ingredient, mesh, result, resultAmount, resultNbt, byHandOnly); } @SuppressWarnings("deprecation") @@ -108,14 +121,15 @@ public class SieveRecipe extends ProbabilityRecipe { buffer.writeId(BuiltInRegistries.ITEM, recipe.mesh); buffer.writeId(BuiltInRegistries.ITEM, recipe.result); RecipeUtil.toNetworkNumberProvider(buffer, recipe.resultAmount); + buffer.writeNbt(recipe.resultNbt); buffer.writeBoolean(recipe.byHandOnly); } } public static class Serializer extends AbstractSerializer { @Override - protected SieveRecipe createSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, boolean byHandOnly) { - return new SieveRecipe(id, ingredient, mesh, result, resultAmount, byHandOnly); + protected SieveRecipe createSieveRecipe(ResourceLocation id, Ingredient ingredient, Item mesh, Item result, NumberProvider resultAmount, @Nullable CompoundTag resultNbt, boolean byHandOnly) { + return new SieveRecipe(id, ingredient, mesh, result, resultAmount, resultNbt, byHandOnly); } } } diff --git a/src/test/java/thedarkcolour/exdeorum/recipe/RecipeSerializationTests.java b/src/test/java/thedarkcolour/exdeorum/recipe/RecipeSerializationTests.java index 672465d3..4b448377 100644 --- a/src/test/java/thedarkcolour/exdeorum/recipe/RecipeSerializationTests.java +++ b/src/test/java/thedarkcolour/exdeorum/recipe/RecipeSerializationTests.java @@ -21,14 +21,17 @@ package thedarkcolour.exdeorum.recipe; import com.google.gson.JsonObject; import io.netty.buffer.Unpooled; import net.minecraft.SharedConstants; +import net.minecraft.nbt.CompoundTag; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.server.Bootstrap; import net.minecraft.tags.BlockTags; import net.minecraft.world.item.Items; +import net.minecraft.world.item.crafting.Ingredient; import net.minecraft.world.item.crafting.Recipe; import net.minecraft.world.item.crafting.RecipeSerializer; import net.minecraft.world.level.block.state.BlockState; import net.minecraft.world.level.material.Fluids; +import net.minecraft.world.level.storage.loot.providers.number.UniformGenerator; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import thedarkcolour.exdeorum.recipe.barrel.FinishedFluidTransformationRecipe; @@ -36,7 +39,10 @@ import thedarkcolour.exdeorum.recipe.barrel.FluidTransformationRecipe; import thedarkcolour.exdeorum.recipe.crook.CrookRecipe; import thedarkcolour.exdeorum.recipe.crucible.CrucibleHeatRecipe; import thedarkcolour.exdeorum.recipe.crucible.FinishedCrucibleHeatRecipe; +import thedarkcolour.exdeorum.recipe.hammer.HammerRecipe; +import thedarkcolour.exdeorum.recipe.sieve.SieveRecipe; +import java.util.function.BiPredicate; import java.util.function.Function; import static org.junit.jupiter.api.Assertions.*; @@ -50,41 +56,42 @@ public class RecipeSerializationTests { } @Test - void crucibleHeatSourceNetwork() { + void networkRecipes() { + CompoundTag testData = new CompoundTag(); + testData.putInt("apple", 12); + testNetwork(new CrucibleHeatRecipe(null, BlockPredicate.blockTag(BlockTags.DIRT), 3), new CrucibleHeatRecipe.Serializer()); + testNetwork(new FluidTransformationRecipe(null, Fluids.WATER, Fluids.LAVA, 1, BlockPredicate.blockTag(BlockTags.DIRT), WeightedList.builder().build(), 1000), new FluidTransformationRecipe.Serializer()); + testNetwork(new CrookRecipe(null, BlockPredicate.blockTag(BlockTags.DIRT), Items.DIAMOND, null, 0.0025f), new CrookRecipe.Serializer()); + testNetwork(new SieveRecipe(null, Ingredient.of(Items.SOUL_SOIL), Items.IRON_AXE, Items.DIAMOND, UniformGenerator.between(1, 3), null, true), new SieveRecipe.Serializer(), SieveRecipe::areEqual); + testNetwork(new SieveRecipe(null, Ingredient.of(Items.SOUL_SOIL), Items.IRON_AXE, Items.DIAMOND, UniformGenerator.between(1, 3), testData, true), new SieveRecipe.Serializer(), SieveRecipe::areEqual); + testNetwork(new HammerRecipe(null, Ingredient.of(Items.SOUL_SOIL), Items.SOUL_SAND, UniformGenerator.between(1, 3), null), new HammerRecipe.Serializer(), HammerRecipe::areEqual); + testNetwork(new HammerRecipe(null, Ingredient.of(Items.SOUL_SOIL), Items.SOUL_SAND, UniformGenerator.between(1, 3), testData), new HammerRecipe.Serializer(), HammerRecipe::areEqual); } @Test - void crucibleHeatSourceJson() { + void jsonRecipes() { testJson(new CrucibleHeatRecipe(null, BlockPredicate.blockTag(BlockTags.DIRT), 3), new CrucibleHeatRecipe.Serializer(), recipe -> { return new FinishedCrucibleHeatRecipe(recipe.id(), recipe.blockPredicate(), recipe.heatValue()); }); - } - - @Test - void barrelFluidTransformationNetwork() { - testNetwork(new FluidTransformationRecipe(null, Fluids.WATER, Fluids.LAVA, 1, BlockPredicate.blockTag(BlockTags.DIRT), WeightedList.builder().build(), 1000), new FluidTransformationRecipe.Serializer()); - } - - @Test - void barrelFluidTransformationJson() { testJson(new FluidTransformationRecipe(null, Fluids.WATER, Fluids.LAVA, 1, BlockPredicate.blockTag(BlockTags.DIRT), WeightedList.builder().build(), 1000), new FluidTransformationRecipe.Serializer(), recipe -> { return new FinishedFluidTransformationRecipe(recipe.getId(), recipe.baseFluid, recipe.resultFluid, recipe.resultColor, recipe.catalyst, recipe.byproducts, recipe.duration); }); } - @Test - void crookNetwork() { - testNetwork(new CrookRecipe(null, BlockPredicate.blockTag(BlockTags.DIRT), Items.DIAMOND, 0.0025f), new CrookRecipe.Serializer()); + // Takes a recipe, uses its serializer to write it to a buffer, then reads it + // back and checks if the recipe it got is the same as the one originally written + private static > void testNetwork(T recipe, RecipeSerializer serializer) { + testNetwork(recipe, serializer, Recipe::equals); } // Takes a recipe, uses its serializer to write it to a buffer, then reads it // back and checks if the recipe it got is the same as the one originally written - private static > void testNetwork(T recipe, RecipeSerializer serializer) { + private static > void testNetwork(T recipe, RecipeSerializer serializer, BiPredicate equalityCheck) { var id = recipe.getId(); var buffer = new FriendlyByteBuf(Unpooled.buffer()); serializer.toNetwork(buffer, recipe); - assertEquals(recipe, serializer.fromNetwork(id, buffer)); + assertTrue(equalityCheck.test(recipe, serializer.fromNetwork(id, buffer))); } private static > void testJson(T recipe, RecipeSerializer serializer, Function toJson) {