User Tools

Site Tools


Sidebar

← Go back to the homepage

Fabric Tutorials

Setup

Basics

These pages are essential must-reads when modding with Fabric, and modding Minecraft in general, if you are new to modding, it is recommended you read the following.

Items

Blocks and Block Entities

Data Generation

World Generation

Commands

These pages will guide you through Mojang's Brigadier library which allows you to create commands with complex arguments and actions.

Events

These pages will guide you through using the many events included in Fabric API, and how to create your own events for you or other mods to use.

Entities

Fluids

Mixins & ASM

These pages will guide you through the usage of SpongePowered's Mixin library, which is a highly complex topic. We recommend you read these pages thoroughly.

Miscellaneous

Yarn

Contribute to Fabric

tutorial:datagen_setup

Getting started with Data Generation

Data Generation is a new module of the Fabric API, it allows you to dynamically generate Recipes, Language Files, Loot Tables, Advancements and pretty much anything with Custom Providers.

First we'll add a new gradle task which will take the code we write to generate data and spit out files Minecraft can read. Every time you modify the code that generates advancements (or anything else datagen can make like loot tables and such) you'll have to run the gradle task runDatagenClient. We will do that later, but first open up your build.gradle file and add the following task:

// ... (The rest of the file)
 
loom {
    runs {
        //
        // This adds a new gradle task that runs the datagen API: "gradlew runDatagenClient"
        //
        datagenClient {
            inherit client
            name "Data Generation"
            vmArg "-Dfabric-api.datagen"
            vmArg "-Dfabric-api.datagen.output-dir=${file("src/main/generated")}"
            vmArg "-Dfabric-api.datagen.modid=${modid}"
 
            runDir "build/datagen"
        }
    }
}
 
//
// Adds the generated files into the jar you distribute to players.
//
sourceSets {
    main {
        resources {
            srcDirs += [
                    'src/main/generated'
            ]
        }
    }
}

You'll notice it makes use of the variable ${modid}. That should be defined in the gradle.properties file. Check and see if you have it there, and if not, you can add it like this:

// .. (The rest of the file)
 
modid=the-name-of-your-mod-change-me-please
 
// .. (The rest of the file)

Next we'll define a new class in our project DataGeneration which implements DataGeneratorEntrypoint.

  • The onInitializeDataGenerator function will be called whenever the gradle task we created earlier (runDatagenClient) is ran.
import net.fabricmc.fabric.api.datagen.v1.DataGeneratorEntrypoint;
import net.fabricmc.fabric.api.datagen.v1.FabricDataGenerator;
 
public class DataGeneration implements DataGeneratorEntrypoint {
 
    @Override
    public void onInitializeDataGenerator(FabricDataGenerator fabricDataGenerator) {
 
    }
}

Now we need to tell fabric about this entry point in our fabric.mod.json file:

{
 
  // ... (The rest of the file)
 
  "entrypoints": {
    "fabric-datagen": [
      "DataGeneration"
    ],
    "main": [
      "AdvancementsTutorial"
    ],
    "client": [
      "AdvancementsTutorialClient"
    ]
  },
 
  // ... (The rest of the file)
 
}

Before continuing further let's see if what we have so far is working, or if we have any errors. Run the runDatagenClient task. You can have your IDE do that for you, or just open the terminal in the root directory of your project and do:

./gradlew runDatagenClient

Read the output and make sure there are no errors.

  • You can safely ignore: com.mojang.authlib.exceptions.InvalidCredentialsException: Status: 401 if it comes up. That error happens because the debug version of Minecraft we're running doesn't try to authenticate our account.

If you do get an error, it's usually pretty explicit about what's missing or wrong, but if you can't seem to figure it out, you might want to head over to the discord, and get some help.

There should be a new folder in src/main called generated. For now it'll be empty, but once we start generating data (like advancements), that is where it'll be saved.

Adding Providers

This is a generic guide on how to add a provider, for more in depth information on each provider, see their respective pages:

In this example, we will be creating a tag provider, as it is the simplest to understand.

Firstly, inside your MyModDatagen class, create a new private static class that extends FabricTagProvider<T>:

If you want, you can place this class in a seperate file, but we recommend it stays in your datagen entrypoint class.

private static class MyTagGenerator extends FabricTagProvider<Item> {
        public MyTagGenerator(FabricDataGenerator dataGenerator) {
            super(dataGenerator, Registries.ITEM);  // for versions 1.19.2 and below, use Registry.ITEM
        }
 
        @Override
        protected void generateTags() {
 
        }
}

We will add some basic tags inside generateTags() for example's sake.

// We will create an item tag called "smelly_items".
private static final TagKey<Item> SMELLY_ITEMS = TagKey.of(RegistryKeys.ITEM, new Identifier("tutorial", "smelly_items"));
 
@Override
protected void generateTags() {
     // This creates a tag builder, where we add slime balls, rotten flesh and everything in the minecraft:dirt item tag.
     getOrCreateTagBuilder(SMELLY_ITEMS)
              .add(Items.SLIME_BALL)
              .add(Items.ROTTEN_FLESH)
              .addOptionalTag(ItemTags.DIRT);
     // This will automatically generate "assets/tutorial/tags/items/smelly_items.json" in the "generated" folder.
}

Now, we will need to register this provider to the data generator in the onInitializeDataGenerator in your entrypoint class like so:

public class DataGeneration implements DataGeneratorEntrypoint {
    @Override
    public void onInitializeDataGenerator(FabricDataGenerator fabricDataGenerator) {
        fabricDataGenerator.addProvider(MyTagGenerator::new);
    }
}

When we run gradlew runDatagenClient, we should see the generated folder forms, and the item tag json should be present:

smelly_items.json
{
  "replace": false,
  "values": [
    "minecraft:slime_ball",
    "minecraft:rotten_flesh",
    {
      "id": "#minecraft:dirt",
      "required": false
    }
  ]
}
tutorial/datagen_setup.txt · Last modified: 2022/12/22 11:43 by jmanc3