#Making a new SpecialCraftingRecipe

1 messages · Page 1 of 1 (latest)

fierce nest
#

I wanted to add a recipe thats takes a water bucket and an other item (soybeans) and outputs a bucket of another liquid (soymilk). However, doing this the usual way gives an empty bucket back (only the water is consumed as water bucket is set to have a empty bucket as a remainder)
This is why I started to set up a SpecialCraftingRecipe and tried to copy how Mojang does it by looking at the code for others SpecialCraftingRecipe. My ultimate goal with this SpecialCraftingRecipe is to override the method getRemainder().
In my data generator class, among my other recipe builders, I added this line:

ComplexRecipeJsonBuilder.create(SoymilkRecipe::new).offerTo(exporter, "mymodname:soymilk");

I also added the class :

public class SoymilkRecipe extends SpecialCraftingRecipe {...}

Whose body doesn't matter that much for now, the only problematic method is getSerializer, this is where my error is coming from. Here is the method:

@Override
public RecipeSerializer<?> getSerializer() {
    return Registry.register(Registries.RECIPE_SERIALIZER, "mymodname:crafting_special_soymilk", new SpecialRecipeSerializer<>(SoymilkRecipe::new));
}

When running the data generation I get this error:
Caused by: java.lang.IllegalStateException: Registry is already frozen (trying to add key ResourceKey[minecraft:recipe_serializer / mymodname:crafting_special_soymilk])
My problem probably comes from my very little understanding of registries and how or when they are initialized and frozen.

narrow pelican
#

You need to register it in or before the onInitialize in the class that implements ModInitializer. If you try it after the registry becomes frozen/immutable.

fierce nest
#

However my method onInitialize, inside my ClientModInitializer, does not have the parameter exporter. And also, why would all the other standard recipes register just fine if the Registry was really frozen ? Is there several Registries and I 'm not using the right one ?

narrow pelican
#

That getSerializer is not a valid approach. Here is a crude example to get an idea:

public class MyMod implements ModInitializer {
    public static final RecipeSerializer<?> RECIPE_SERIALIZER = Registry.register(Registries.RECIPE_SERIALIZER, "mymodname:crafting_special_soymilk", new SpecialRecipeSerializer<>(SoymilkRecipe::new));

    @Override
    public void onInitialize() {
    }
}

public class MySerializerClass extends A implements B {
    @Override
    public RecipeSerializer<?> getSerializer() {
        return MyMod.RECIPE_SERIALIZER;
    }
}
narrow pelican
fierce nest
#

Unfortunately it doesn't seem to solve the issue 🤔 Even thought the RECIPE_SERIALIZER is defined staticly in MyMod, the call to the getSerializer() still get called during data generation because the line

ComplexRecipeJsonBuilder.create(SoymilkRecipe::new).offerTo(exporter, "mycozymod:soymilk");

Is in the method public void generate(RecipeExporter exporter) in the class private static class MyRecipeGenerator extends FabricRecipeProvider

narrow pelican
#

Even during data generation the onInitialize should be called prior to the provider class, so it should not be an issue. If it is an issue there may be more wrong.

I see ClientModInitializer but that is client-side side. You need to register the recipe server-side, thus the serializer should also be server-side. (Or main to be precise.)