Fixed some recipe codec issues

This commit is contained in:
Frank 2023-12-19 17:47:31 +01:00
parent 4aff004c8b
commit 4f01267940
4 changed files with 41 additions and 54 deletions

View file

@ -49,7 +49,7 @@ public abstract class AbstractSimpleRecipeBuilder<T extends AbstractSimpleRecipe
protected boolean checkRecipe() {
if (primaryInput == null) {
if (primaryInput == null || primaryInput.isEmpty()) {
BCLib.LOGGER.warning(
"Primary input for Recipe can't be 'null', recipe {} will be ignored!",
id

View file

@ -13,6 +13,7 @@ import net.minecraft.nbt.CompoundTag;
import net.minecraft.network.FriendlyByteBuf;
import net.minecraft.resources.ResourceLocation;
import net.minecraft.tags.TagKey;
import net.minecraft.util.ExtraCodecs;
import net.minecraft.world.Container;
import net.minecraft.world.item.Item;
import net.minecraft.world.item.ItemStack;
@ -27,6 +28,7 @@ import net.fabricmc.api.EnvType;
import net.fabricmc.api.Environment;
import java.util.List;
import java.util.Optional;
public class AlloyingRecipe implements Recipe<Container>, UnknownReceipBookCategory {
public final static String GROUP = "alloying";
@ -62,6 +64,16 @@ public class AlloyingRecipe implements Recipe<Container>, UnknownReceipBookCateg
);
}
public AlloyingRecipe(
List<Ingredient> inputs,
Optional<String> group,
ItemStack output,
float experience,
int smeltTime
) {
this(inputs, group.orElse(null), output, experience, smeltTime);
}
public AlloyingRecipe(
String group,
Ingredient primaryInput,
@ -216,8 +228,8 @@ public class AlloyingRecipe implements Recipe<Container>, UnknownReceipBookCateg
Codec.list(Ingredient.CODEC_NONEMPTY)
.fieldOf("ingredients")
.forGetter(recipe -> List.of(recipe.primaryInput, recipe.secondaryInput)),
Codec.STRING.optionalFieldOf("group", "")
.forGetter(recipe -> recipe.group),
ExtraCodecs.strictOptionalField(Codec.STRING, "group")
.forGetter(recipe -> Optional.ofNullable(recipe.group)),
ItemUtil.CODEC_ITEM_STACK_WITH_NBT.fieldOf("result").forGetter(recipe -> recipe.output),
Codec.FLOAT.optionalFieldOf("experience", 0f).forGetter(recipe -> recipe.experience),
Codec.INT.optionalFieldOf("smelttime", 350).forGetter(recipe -> recipe.smeltTime)

View file

@ -14,8 +14,6 @@ import net.minecraft.world.item.Item;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.item.crafting.Ingredient;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Optional;
import org.jetbrains.annotations.Nullable;
@ -59,61 +57,34 @@ public class ItemUtil {
.forGetter((itemStack) -> Optional.ofNullable(itemStack.getTag()))
).apply(instance, ItemStack::new));
public static Codec<Ingredient> CODEC_INGREDIENT_WITH_NBT = ingredientCodec(true);
public static Codec<Ingredient> CODEC_INGREDIENT_WITH_NBT_NOT_EMPTY = ingredientCodec(false);
private static final Codec<Ingredient.ItemValue> CODEC_NBT_ITEM_VALUE = RecordCodecBuilder.create((instance) -> instance
.group(CODEC_ITEM_STACK_WITH_NBT.fieldOf("item").forGetter((itemValue) -> itemValue.item()))
.apply(instance, Ingredient.ItemValue::new));
private static final Codec<Ingredient.Value> VALUE_CODEC = ExtraCodecs
.xor(CODEC_NBT_ITEM_VALUE, Ingredient.TagValue.CODEC)
.xmap(
(either) -> either.map((itemValue) -> itemValue, (tagValue) -> tagValue),
(value) -> {
if (value instanceof Ingredient.TagValue tagValue) {
return Either.right(tagValue);
} else if (value instanceof Ingredient.ItemValue itemValue) {
return Either.left(itemValue);
} else {
throw new UnsupportedOperationException(
"This is neither an nbt-item value nor a tag value.");
}
}
);
private static Codec<Ingredient> ingredientCodec(boolean allowEmpty) {
record NbtItemValue(ItemStack item) implements Ingredient.Value {
static final Codec<NbtItemValue> CODEC = RecordCodecBuilder.create((instance) -> instance
.group(CODEC_ITEM_STACK_WITH_NBT.fieldOf("item").forGetter((itemValue) -> itemValue.item))
.apply(instance, NbtItemValue::new));
public boolean equals(Object object) {
if (object instanceof NbtItemValue itemValue) {
return ItemStack.isSameItemSameTags(itemValue.item, this.item)
&& itemValue.item.getCount() == this.item.getCount();
} else if (object instanceof Ingredient.ItemValue itemValue) {
return ItemStack.isSameItemSameTags(itemValue.item(), this.item)
&& itemValue.item().getCount() == this.item.getCount();
} else {
return false;
}
}
public Collection<ItemStack> getItems() {
return Collections.singleton(this.item);
}
public ItemStack item() {
return this.item;
}
}
Codec<Ingredient.Value> VALUE_CODEC = ExtraCodecs
.xor(NbtItemValue.CODEC, Ingredient.TagValue.CODEC)
.xmap(
(either) -> either.map((itemValue) -> itemValue, (tagValue) -> tagValue),
(value) -> {
if (value instanceof Ingredient.TagValue tagValue) {
return Either.right(tagValue);
} else if (value instanceof NbtItemValue itemValue) {
return Either.left(itemValue);
} else {
throw new UnsupportedOperationException(
"This is neither an nbt-item value nor a tag value.");
}
}
);
Codec<Ingredient.Value[]> codec = Codec.list(VALUE_CODEC).comapFlatMap((list) ->
!allowEmpty && list.size() < 1
Codec<Ingredient.Value[]> LIST_CODEC = Codec.list(VALUE_CODEC).comapFlatMap((list) ->
!allowEmpty && list.isEmpty()
? DataResult.error(() -> "Item array cannot be empty, at least one item must be defined")
: DataResult.success(list.toArray(new Ingredient.Value[0]))
, List::of);
return ExtraCodecs.either(codec, VALUE_CODEC).flatComapMap(
return ExtraCodecs.either(LIST_CODEC, VALUE_CODEC).flatComapMap(
(either) -> either.map(Ingredient::new, (value) -> new Ingredient(new Ingredient.Value[]{value})),
(ingredient) -> {
if (ingredient.values.length == 1) {
@ -126,4 +97,7 @@ public class ItemUtil {
}
);
}
public static Codec<Ingredient> CODEC_INGREDIENT_WITH_NBT = ingredientCodec(true);
public static Codec<Ingredient> CODEC_INGREDIENT_WITH_NBT_NOT_EMPTY = ingredientCodec(false);
}

View file

@ -1,7 +1,7 @@
accessWidener v1 named
# Classes
accessible class net/minecraft/server/MinecraftServer$ReloadableResources
accessible class net/minecraft/server/MinecraftServer$ReloadableResources
accessible class net/minecraft/world/level/levelgen/SurfaceRules$Context
accessible class net/minecraft/world/level/levelgen/SurfaceRules$Condition
accessible class net/minecraft/world/level/levelgen/SurfaceRules$SurfaceRule
@ -41,6 +41,7 @@ accessible method net/minecraft/world/level/levelgen/structure/pools/SinglePoolE
accessible method net/minecraft/world/level/levelgen/structure/pools/LegacySinglePoolElement <init> (Lcom/mojang/datafixers/util/Either;Lnet/minecraft/core/Holder;Lnet/minecraft/world/level/levelgen/structure/pools/StructureTemplatePool$Projection;)V
accessible method net/minecraft/world/item/crafting/Ingredient <init> ([Lnet/minecraft/world/item/crafting/Ingredient$Value;)V
accessible method net/minecraft/world/item/crafting/Ingredient$TagValue <init> (Lnet/minecraft/tags/TagKey;)V
accessible method net/minecraft/world/item/crafting/Ingredient$ItemValue <init> (Lnet/minecraft/world/item/ItemStack;)V
#Fields
accessible field net/minecraft/world/entity/ai/village/poi/PoiTypes TYPE_BY_STATE Ljava/util/Map;