<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en-GB">
	<id>https://forge.gemwire.uk/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Nexus-Dino</id>
	<title>Forge Community Wiki - User contributions [en-gb]</title>
	<link rel="self" type="application/atom+xml" href="https://forge.gemwire.uk/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Nexus-Dino"/>
	<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/wiki/Special:Contributions/Nexus-Dino"/>
	<updated>2026-06-02T07:36:35Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.35.0</generator>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Block_Entity_Renderer&amp;diff=3354</id>
		<title>Block Entity Renderer</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Block_Entity_Renderer&amp;diff=3354"/>
		<updated>2022-10-08T08:30:58Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: /* Parameters */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A &amp;lt;code&amp;gt;BlockEntityRenderer&amp;lt;/code&amp;gt; or &amp;lt;code&amp;gt;BER&amp;lt;/code&amp;gt; is used to render blocks in a way that cannot be represented with a static baked model (JSON, OBJ, B3D, etc.). A block entity renderer requires the block to have a &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Creating a BER ==&lt;br /&gt;
To create a BER, create a class that inherits from &amp;lt;code&amp;gt;BlockEntityRenderer&amp;lt;/code&amp;gt;. It takes a generic argument specifying the block's &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; class. The generic argument is used in the BER's &amp;lt;code&amp;gt;render&amp;lt;/code&amp;gt; method.&lt;br /&gt;
&lt;br /&gt;
Only one BER exists for a given &amp;lt;code&amp;gt;BlockEntityType&amp;lt;/code&amp;gt;. Therefore, values that are specific to a single instance in the world should be stored in the block entity being passed to the renderer rather than in the BER itself. For example, an integer that increments every frame, if stored in the BER, will increment every frame for every block entity of this type in the world.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;code&amp;gt; render &amp;lt;/code&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
This method is called every frame in order to render the block entity.&lt;br /&gt;
&lt;br /&gt;
=== Parameters ===&lt;br /&gt;
* &amp;lt;code&amp;gt;blockEntity&amp;lt;/code&amp;gt;: This is the instance of the block entity being rendered.&lt;br /&gt;
* &amp;lt;code&amp;gt;partialTick&amp;lt;/code&amp;gt;: The amount of time, in fractions of a tick, that has passed since the last full tick.&lt;br /&gt;
* &amp;lt;code&amp;gt;poseStack&amp;lt;/code&amp;gt;: A stack holding four-dimensional matrix entries offset to the current position of the block entity.&lt;br /&gt;
* &amp;lt;code&amp;gt;bufferSource&amp;lt;/code&amp;gt;: A rendering buffer able to access a vertex consumer.&lt;br /&gt;
* &amp;lt;code&amp;gt;combinedLight&amp;lt;/code&amp;gt;: An integer of the current light value on the block entity.&lt;br /&gt;
* &amp;lt;code&amp;gt;combinedOverlay&amp;lt;/code&amp;gt;: An integer set to the current overlay of the block entity, usually &amp;lt;code&amp;gt;OverlayTexture#NO_OVERLAY&amp;lt;/code&amp;gt; or 655,360.&lt;br /&gt;
&lt;br /&gt;
==Registering a BER==&lt;br /&gt;
In order to register a BER, you must subscribe to the &amp;lt;code&amp;gt;EntityRenderersEvent$RegisterRenderers&amp;lt;/code&amp;gt; event on the mod event bus and call &amp;lt;code&amp;gt;#registerBlockEntityRenderer&amp;lt;/code&amp;gt;.&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Making_Entities&amp;diff=3340</id>
		<title>Making Entities</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Making_Entities&amp;diff=3340"/>
		<updated>2022-10-06T06:02:19Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: Fix Attributes Section&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Under construction}}&lt;br /&gt;
&lt;br /&gt;
Entities are core to the Minecraft world and make up all movable objects that do not fall under [[Making Blocks|Blocks]] or [[Block Entities]]. Entities can tick and be controlled by AI or player input. This article serves as a guide for setting up a basic entity. It does not involve setting up the rendering for an entity, which is a required step to be able to see an entity in-game without crashing. See [[Entity Renderer]] for more information on entity rendering and setup.&lt;br /&gt;
&lt;br /&gt;
== Entity Type ==&lt;br /&gt;
Much of the identity of an entity is determined by its '''entity type'''. This contains information universal to an entity. An entity type must exist and be [[Registration|registered]] for the corresponding entity to be summonable. &lt;br /&gt;
&lt;br /&gt;
=== Creating the Builder ===&lt;br /&gt;
The primary way to make an &amp;lt;code&amp;gt;EntityType&amp;lt;/code&amp;gt; is to create and configure an &amp;lt;code&amp;gt;EntityType$Builder&amp;lt;/code&amp;gt;. Creating an entity type builder is done using the static factory &amp;lt;code&amp;gt;EntityType.Builder#of&amp;lt;/code&amp;gt;. It requires two parameters: an &amp;lt;code&amp;gt;EntityType.EntityFactory&amp;lt;/code&amp;gt; and a &amp;lt;code&amp;gt;MobCategory&amp;lt;/code&amp;gt;.&lt;br /&gt;
The entity factory is usually an entity class with a constructor taking its own &amp;lt;code&amp;gt;EntityType&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;Level&amp;lt;/code&amp;gt; of the form &amp;lt;code&amp;gt;MyEntity::new&amp;lt;/code&amp;gt;. This requires a class of the name &amp;lt;code&amp;gt;MyEntity&amp;lt;/code&amp;gt; to actually exist (see [[#Entity Class|the entity class section]] for more info).&lt;br /&gt;
The mob category is an enum describing mostly spawning properties about a category of mobs. This includes:&lt;br /&gt;
&amp;lt;ul&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;How many entities in a given mob category can spawn per chunk&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;Whether the entity is friendly (and therefore will spawn in peaceful difficulty)&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;Whether the entity is persistent (and therefore will save to disk and be reloaded)&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;How many blocks away a player must be for an entity in a given mob category to despawn&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;/ul&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Configuring the Builder ===&lt;br /&gt;
An entity type builder by itself is not very useful. It must be configured to match the desired properties of the entity.&lt;br /&gt;
The possible properties that can be configured are listed below:&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot; border=1&lt;br /&gt;
! Method !! Default Value !! Description&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;sized&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 0.6 meters wide by 1.8 meters tall (player dimensions) || Sets the default pose dimensions of the entity in order of square base width then height in meters/blocks. A value of 1.0 would be equivalent to the length of 1 full block. The base cannot be configured with a separate width and length.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;noSummon&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Can summon || Calling this prevents spawning the entity through &amp;lt;code&amp;gt;/summon&amp;lt;/code&amp;gt;; intended for internal entities that a user should not be able to create. This also prevents summoning through natural spawning in biomes, if it is configured.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;noSave&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Can save || Calling this prevents the entity from ever saving to disk. Unloading a chunk with a &amp;lt;code&amp;gt;noSave&amp;lt;/code&amp;gt; entity will effectively delete the entity.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;fireImmune&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Vulnerable to fire || Calling this prevents the entity from taking any fire/lava damage.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;clientTrackingRange&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 5 chunks || Sets the maximum range in chunks in which players should be sent update packet information about the entity. Sending update information about an entity to a player is known as the player ''tracking'' that entity. If the player is outside this chunk range, they will not know of the entity's existence.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;immuneTo&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Empty set of blocks || Effectively useless for modding purposes.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;canSpawnFarFromPlayer&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || True for &amp;lt;code&amp;gt;MobCategory.CREATURE&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;MobCategory.MISC&amp;lt;/code&amp;gt;, false otherwise. || Calling this allows an entity to spawn outside of the despawn distance of its mob category.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;updateInterval&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 3 ticks || How often, in ticks, update packets should be sent to all client players tracking this entity (see &amp;lt;code&amp;gt;clientTrackingRange&amp;lt;/code&amp;gt;). The update packets contain information like position, rotation, and velocity. They may be sent more quickly than this interval during specific actions.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;setShouldReceiveVelocityUpdates&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || true || Sets whether tracking client players should receive velocity information in update interval packets. If false, velocity information will not be sent to clients unless necessary.&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
=== Building the Builder ===&lt;br /&gt;
After creating and configuring the entity type builder, it must be built. This requires the modid and name of the entity type. For an entity type with the name &amp;quot;example_monster&amp;quot; in the mod &amp;quot;examplemod&amp;quot;, this would look like &amp;lt;code&amp;gt;builder.build(&amp;quot;examplemod:example_monster&amp;quot;)&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== Tying It Together ===&lt;br /&gt;
Given the above information, a basic EntityType might look like the following:&lt;br /&gt;
{{Tabs/Code Snippets&lt;br /&gt;
|java=EntityType.Builder.of(ExampleMonsterEntity::new, MobCategory.MONSTER)&lt;br /&gt;
    .sized(1.0F, 2.0F)&lt;br /&gt;
    .fireImmune()&lt;br /&gt;
    .updateInterval(1)&lt;br /&gt;
    .build(&amp;quot;examplemod:example_monster&amp;quot;)&lt;br /&gt;
}}&lt;br /&gt;
To function, this example requires that an entity class of the name &amp;lt;code&amp;gt;ExampleMonsterEntity&amp;lt;/code&amp;gt; exist along with the entity type being [[Registration|registered]].&lt;br /&gt;
&lt;br /&gt;
== Entity Class ==&lt;br /&gt;
Alongside an entity type, an entity requires a class outlining its behavior and any information that may change from one instance to another. All entities must extend from the base class &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;. However, some entities should extend from specific subclasses instead. For a completely generic entity, use &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;. For a living entity with health, potion effects, and an inventory, use &amp;lt;code&amp;gt;LivingEntity&amp;lt;/code&amp;gt;. For a living entity with movement AI and AI goals, use &amp;lt;code&amp;gt;Mob&amp;lt;/code&amp;gt;. There are also many other entity subclasses which can be found through your IDE and picked depending on the scenario.&lt;br /&gt;
&lt;br /&gt;
Once picking a target superclass to extend, an entity class should be created and the constructor should be setup. It should look something like this:&lt;br /&gt;
{{Tabs/Code Snippets|&lt;br /&gt;
java=public class ExampleMonsterEntity extends Mob {&lt;br /&gt;
    public ExampleMonsterEntity(EntityType&amp;lt;? extends Mob&amp;gt; entityType, Level level) {&lt;br /&gt;
        super(entityType, level);&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
To define custom behavior, methods must be overriden. Your IDE should have a feature to list all possible methods to override, although some common ones might be: &amp;lt;code&amp;gt;customServerAiStep&amp;lt;/code&amp;gt; for server AI, &amp;lt;code&amp;gt;tick&amp;lt;/code&amp;gt; for code to execute each tick on client/server, and &amp;lt;code&amp;gt;registerGoals&amp;lt;/code&amp;gt; to setup AI goals.&lt;br /&gt;
&lt;br /&gt;
== Entity Attributes ==&lt;br /&gt;
Since 1.17 and later versions, you **MUST** define attributes if your entity class extends &amp;lt;code&amp;gt;LivingEntity&amp;lt;/code&amp;gt; or any other class that inherits from it. In Attributes, you can define:&lt;br /&gt;
&lt;br /&gt;
* Max Health&lt;br /&gt;
* Movement Speed&lt;br /&gt;
* Attack Damage&lt;br /&gt;
&lt;br /&gt;
and more...&lt;br /&gt;
&lt;br /&gt;
In your Entity class, create a static method that creates your attributes:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
public static AttributeSupplier.Builder createAttributes()&lt;br /&gt;
{&lt;br /&gt;
      return createHostileAttributes().add(Attributes.MAX_HEALTH, 40.0F).add(Attributes.ATTACK_DAMAGE, 10.0F);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Natural Spawning ==&lt;br /&gt;
To make entities naturally spawn, they must be added to the spawn list for each biome that the entity should spawn in. This can be achieved with a [[Biome Modifiers#Add Spawns|&amp;lt;code&amp;gt;forge:add_spawns&amp;lt;/code&amp;gt; biome modifier]].&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Making_Entities&amp;diff=3339</id>
		<title>Making Entities</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Making_Entities&amp;diff=3339"/>
		<updated>2022-10-06T05:58:11Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: Add Entity Attributes Section&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Under construction}}&lt;br /&gt;
&lt;br /&gt;
Entities are core to the Minecraft world and make up all movable objects that do not fall under [[Making Blocks|Blocks]] or [[Block Entities]]. Entities can tick and be controlled by AI or player input. This article serves as a guide for setting up a basic entity. It does not involve setting up the rendering for an entity, which is a required step to be able to see an entity in-game without crashing. See [[Entity Renderer]] for more information on entity rendering and setup.&lt;br /&gt;
&lt;br /&gt;
== Entity Type ==&lt;br /&gt;
Much of the identity of an entity is determined by its '''entity type'''. This contains information universal to an entity. An entity type must exist and be [[Registration|registered]] for the corresponding entity to be summonable. &lt;br /&gt;
&lt;br /&gt;
=== Creating the Builder ===&lt;br /&gt;
The primary way to make an &amp;lt;code&amp;gt;EntityType&amp;lt;/code&amp;gt; is to create and configure an &amp;lt;code&amp;gt;EntityType$Builder&amp;lt;/code&amp;gt;. Creating an entity type builder is done using the static factory &amp;lt;code&amp;gt;EntityType.Builder#of&amp;lt;/code&amp;gt;. It requires two parameters: an &amp;lt;code&amp;gt;EntityType.EntityFactory&amp;lt;/code&amp;gt; and a &amp;lt;code&amp;gt;MobCategory&amp;lt;/code&amp;gt;.&lt;br /&gt;
The entity factory is usually an entity class with a constructor taking its own &amp;lt;code&amp;gt;EntityType&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;Level&amp;lt;/code&amp;gt; of the form &amp;lt;code&amp;gt;MyEntity::new&amp;lt;/code&amp;gt;. This requires a class of the name &amp;lt;code&amp;gt;MyEntity&amp;lt;/code&amp;gt; to actually exist (see [[#Entity Class|the entity class section]] for more info).&lt;br /&gt;
The mob category is an enum describing mostly spawning properties about a category of mobs. This includes:&lt;br /&gt;
&amp;lt;ul&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;How many entities in a given mob category can spawn per chunk&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;Whether the entity is friendly (and therefore will spawn in peaceful difficulty)&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;Whether the entity is persistent (and therefore will save to disk and be reloaded)&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;How many blocks away a player must be for an entity in a given mob category to despawn&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;/ul&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Configuring the Builder ===&lt;br /&gt;
An entity type builder by itself is not very useful. It must be configured to match the desired properties of the entity.&lt;br /&gt;
The possible properties that can be configured are listed below:&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot; border=1&lt;br /&gt;
! Method !! Default Value !! Description&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;sized&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 0.6 meters wide by 1.8 meters tall (player dimensions) || Sets the default pose dimensions of the entity in order of square base width then height in meters/blocks. A value of 1.0 would be equivalent to the length of 1 full block. The base cannot be configured with a separate width and length.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;noSummon&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Can summon || Calling this prevents spawning the entity through &amp;lt;code&amp;gt;/summon&amp;lt;/code&amp;gt;; intended for internal entities that a user should not be able to create. This also prevents summoning through natural spawning in biomes, if it is configured.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;noSave&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Can save || Calling this prevents the entity from ever saving to disk. Unloading a chunk with a &amp;lt;code&amp;gt;noSave&amp;lt;/code&amp;gt; entity will effectively delete the entity.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;fireImmune&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Vulnerable to fire || Calling this prevents the entity from taking any fire/lava damage.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;clientTrackingRange&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 5 chunks || Sets the maximum range in chunks in which players should be sent update packet information about the entity. Sending update information about an entity to a player is known as the player ''tracking'' that entity. If the player is outside this chunk range, they will not know of the entity's existence.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;immuneTo&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Empty set of blocks || Effectively useless for modding purposes.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;canSpawnFarFromPlayer&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || True for &amp;lt;code&amp;gt;MobCategory.CREATURE&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;MobCategory.MISC&amp;lt;/code&amp;gt;, false otherwise. || Calling this allows an entity to spawn outside of the despawn distance of its mob category.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;updateInterval&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 3 ticks || How often, in ticks, update packets should be sent to all client players tracking this entity (see &amp;lt;code&amp;gt;clientTrackingRange&amp;lt;/code&amp;gt;). The update packets contain information like position, rotation, and velocity. They may be sent more quickly than this interval during specific actions.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;setShouldReceiveVelocityUpdates&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || true || Sets whether tracking client players should receive velocity information in update interval packets. If false, velocity information will not be sent to clients unless necessary.&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
=== Building the Builder ===&lt;br /&gt;
After creating and configuring the entity type builder, it must be built. This requires the modid and name of the entity type. For an entity type with the name &amp;quot;example_monster&amp;quot; in the mod &amp;quot;examplemod&amp;quot;, this would look like &amp;lt;code&amp;gt;builder.build(&amp;quot;examplemod:example_monster&amp;quot;)&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== Tying It Together ===&lt;br /&gt;
Given the above information, a basic EntityType might look like the following:&lt;br /&gt;
{{Tabs/Code Snippets&lt;br /&gt;
|java=EntityType.Builder.of(ExampleMonsterEntity::new, MobCategory.MONSTER)&lt;br /&gt;
    .sized(1.0F, 2.0F)&lt;br /&gt;
    .fireImmune()&lt;br /&gt;
    .updateInterval(1)&lt;br /&gt;
    .build(&amp;quot;examplemod:example_monster&amp;quot;)&lt;br /&gt;
}}&lt;br /&gt;
To function, this example requires that an entity class of the name &amp;lt;code&amp;gt;ExampleMonsterEntity&amp;lt;/code&amp;gt; exist along with the entity type being [[Registration|registered]].&lt;br /&gt;
&lt;br /&gt;
== Entity Class ==&lt;br /&gt;
Alongside an entity type, an entity requires a class outlining its behavior and any information that may change from one instance to another. All entities must extend from the base class &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;. However, some entities should extend from specific subclasses instead. For a completely generic entity, use &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;. For a living entity with health, potion effects, and an inventory, use &amp;lt;code&amp;gt;LivingEntity&amp;lt;/code&amp;gt;. For a living entity with movement AI and AI goals, use &amp;lt;code&amp;gt;Mob&amp;lt;/code&amp;gt;. There are also many other entity subclasses which can be found through your IDE and picked depending on the scenario.&lt;br /&gt;
&lt;br /&gt;
Once picking a target superclass to extend, an entity class should be created and the constructor should be setup. It should look something like this:&lt;br /&gt;
{{Tabs/Code Snippets|&lt;br /&gt;
java=public class ExampleMonsterEntity extends Mob {&lt;br /&gt;
    public ExampleMonsterEntity(EntityType&amp;lt;? extends Mob&amp;gt; entityType, Level level) {&lt;br /&gt;
        super(entityType, level);&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
To define custom behavior, methods must be overriden. Your IDE should have a feature to list all possible methods to override, although some common ones might be: &amp;lt;code&amp;gt;customServerAiStep&amp;lt;/code&amp;gt; for server AI, &amp;lt;code&amp;gt;tick&amp;lt;/code&amp;gt; for code to execute each tick on client/server, and &amp;lt;code&amp;gt;registerGoals&amp;lt;/code&amp;gt; to setup AI goals.&lt;br /&gt;
&lt;br /&gt;
== Entity Attributes ==&lt;br /&gt;
Since 1.17 and later versions, you **MUST** define attributes if your entity class extends &amp;lt;code&amp;gt;LivingEntity&amp;lt;/code&amp;gt; or any other class that inherits from it. In Attributes, you can define:&lt;br /&gt;
&lt;br /&gt;
* Max Health&lt;br /&gt;
* Movement Speed&lt;br /&gt;
* Attack Damage&lt;br /&gt;
&lt;br /&gt;
and more...&lt;br /&gt;
&lt;br /&gt;
In your Entity class, create a static method that creates your attributes:&lt;br /&gt;
&amp;lt;code&amp;gt;&lt;br /&gt;
// In your Entity class...&lt;br /&gt;
&lt;br /&gt;
public static AttributeSupplier.Builder setAttributes()&lt;br /&gt;
{&lt;br /&gt;
      return createHostileAttributes().add(Attributes.MAX_HEALTH);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/code&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Natural Spawning ==&lt;br /&gt;
To make entities naturally spawn, they must be added to the spawn list for each biome that the entity should spawn in. This can be achieved with a [[Biome Modifiers#Add Spawns|&amp;lt;code&amp;gt;forge:add_spawns&amp;lt;/code&amp;gt; biome modifier]].&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Making_Entities&amp;diff=3338</id>
		<title>Making Entities</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Making_Entities&amp;diff=3338"/>
		<updated>2022-10-06T05:40:38Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: /* Tying It Together */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Under construction}}&lt;br /&gt;
&lt;br /&gt;
Entities are core to the Minecraft world and make up all movable objects that do not fall under [[Making Blocks|Blocks]] or [[Block Entities]]. Entities can tick and be controlled by AI or player input. This article serves as a guide for setting up a basic entity. It does not involve setting up the rendering for an entity, which is a required step to be able to see an entity in-game without crashing. See [[Entity Renderer]] for more information on entity rendering and setup.&lt;br /&gt;
&lt;br /&gt;
== Entity Type ==&lt;br /&gt;
Much of the identity of an entity is determined by its '''entity type'''. This contains information universal to an entity. An entity type must exist and be [[Registration|registered]] for the corresponding entity to be summonable. &lt;br /&gt;
&lt;br /&gt;
=== Creating the Builder ===&lt;br /&gt;
The primary way to make an &amp;lt;code&amp;gt;EntityType&amp;lt;/code&amp;gt; is to create and configure an &amp;lt;code&amp;gt;EntityType$Builder&amp;lt;/code&amp;gt;. Creating an entity type builder is done using the static factory &amp;lt;code&amp;gt;EntityType.Builder#of&amp;lt;/code&amp;gt;. It requires two parameters: an &amp;lt;code&amp;gt;EntityType.EntityFactory&amp;lt;/code&amp;gt; and a &amp;lt;code&amp;gt;MobCategory&amp;lt;/code&amp;gt;.&lt;br /&gt;
The entity factory is usually an entity class with a constructor taking its own &amp;lt;code&amp;gt;EntityType&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;Level&amp;lt;/code&amp;gt; of the form &amp;lt;code&amp;gt;MyEntity::new&amp;lt;/code&amp;gt;. This requires a class of the name &amp;lt;code&amp;gt;MyEntity&amp;lt;/code&amp;gt; to actually exist (see [[#Entity Class|the entity class section]] for more info).&lt;br /&gt;
The mob category is an enum describing mostly spawning properties about a category of mobs. This includes:&lt;br /&gt;
&amp;lt;ul&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;How many entities in a given mob category can spawn per chunk&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;Whether the entity is friendly (and therefore will spawn in peaceful difficulty)&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;Whether the entity is persistent (and therefore will save to disk and be reloaded)&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;li&amp;gt;How many blocks away a player must be for an entity in a given mob category to despawn&amp;lt;/li&amp;gt;&lt;br /&gt;
&amp;lt;/ul&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Configuring the Builder ===&lt;br /&gt;
An entity type builder by itself is not very useful. It must be configured to match the desired properties of the entity.&lt;br /&gt;
The possible properties that can be configured are listed below:&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot; border=1&lt;br /&gt;
! Method !! Default Value !! Description&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;sized&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 0.6 meters wide by 1.8 meters tall (player dimensions) || Sets the default pose dimensions of the entity in order of square base width then height in meters/blocks. A value of 1.0 would be equivalent to the length of 1 full block. The base cannot be configured with a separate width and length.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;noSummon&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Can summon || Calling this prevents spawning the entity through &amp;lt;code&amp;gt;/summon&amp;lt;/code&amp;gt;; intended for internal entities that a user should not be able to create. This also prevents summoning through natural spawning in biomes, if it is configured.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;noSave&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Can save || Calling this prevents the entity from ever saving to disk. Unloading a chunk with a &amp;lt;code&amp;gt;noSave&amp;lt;/code&amp;gt; entity will effectively delete the entity.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;fireImmune&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Vulnerable to fire || Calling this prevents the entity from taking any fire/lava damage.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;clientTrackingRange&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 5 chunks || Sets the maximum range in chunks in which players should be sent update packet information about the entity. Sending update information about an entity to a player is known as the player ''tracking'' that entity. If the player is outside this chunk range, they will not know of the entity's existence.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;immuneTo&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || Empty set of blocks || Effectively useless for modding purposes.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;canSpawnFarFromPlayer&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || True for &amp;lt;code&amp;gt;MobCategory.CREATURE&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;MobCategory.MISC&amp;lt;/code&amp;gt;, false otherwise. || Calling this allows an entity to spawn outside of the despawn distance of its mob category.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;updateInterval&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || 3 ticks || How often, in ticks, update packets should be sent to all client players tracking this entity (see &amp;lt;code&amp;gt;clientTrackingRange&amp;lt;/code&amp;gt;). The update packets contain information like position, rotation, and velocity. They may be sent more quickly than this interval during specific actions.&lt;br /&gt;
|-&lt;br /&gt;
| &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;setShouldReceiveVelocityUpdates&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; || true || Sets whether tracking client players should receive velocity information in update interval packets. If false, velocity information will not be sent to clients unless necessary.&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
=== Building the Builder ===&lt;br /&gt;
After creating and configuring the entity type builder, it must be built. This requires the modid and name of the entity type. For an entity type with the name &amp;quot;example_monster&amp;quot; in the mod &amp;quot;examplemod&amp;quot;, this would look like &amp;lt;code&amp;gt;builder.build(&amp;quot;examplemod:example_monster&amp;quot;)&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
===Tying It Together===&lt;br /&gt;
Given the above information, a basic EntityType might look like the following:{{Tabs/Code Snippets&lt;br /&gt;
|java=EntityType.Builder.of(ExampleMonsterEntity::new, MobCategory.MONSTER)&lt;br /&gt;
    .sized(1.0F, 2.0F)&lt;br /&gt;
    .fireImmune()&lt;br /&gt;
    .updateInterval(1)&lt;br /&gt;
    .build(&amp;quot;examplemod:example_monster&amp;quot;)&lt;br /&gt;
}}To function, this example requires that an entity class of the name &amp;lt;code&amp;gt;ExampleMonsterEntity&amp;lt;/code&amp;gt; exist along with the entity type being [[Registration|registered]].&lt;br /&gt;
&lt;br /&gt;
== Entity Class ==&lt;br /&gt;
Alongside an entity type, an entity requires a class outlining its behavior and any information that may change from one instance to another. All entities must extend from the base class &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;. However, some entities should extend from specific subclasses instead. For a completely generic entity, use &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;. For a living entity with health, potion effects, and an inventory, use &amp;lt;code&amp;gt;LivingEntity&amp;lt;/code&amp;gt;. For a living entity with movement AI and AI goals, use &amp;lt;code&amp;gt;Mob&amp;lt;/code&amp;gt;. There are also many other entity subclasses which can be found through your IDE and picked depending on the scenario.&lt;br /&gt;
&lt;br /&gt;
Once picking a target superclass to extend, an entity class should be created and the constructor should be setup. It should look something like this:&lt;br /&gt;
{{Tabs/Code Snippets|&lt;br /&gt;
java=public class ExampleMonsterEntity extends Mob {&lt;br /&gt;
    public ExampleMonsterEntity(EntityType&amp;lt;? extends Mob&amp;gt; entityType, Level level) {&lt;br /&gt;
        super(entityType, level);&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
To define custom behavior, methods must be overriden. Your IDE should have a feature to list all possible methods to override, although some common ones might be: &amp;lt;code&amp;gt;customServerAiStep&amp;lt;/code&amp;gt; for server AI, &amp;lt;code&amp;gt;tick&amp;lt;/code&amp;gt; for code to execute each tick on client/server, and &amp;lt;code&amp;gt;registerGoals&amp;lt;/code&amp;gt; to setup AI goals.&lt;br /&gt;
&lt;br /&gt;
== Natural Spawning ==&lt;br /&gt;
To make entities naturally spawn, they must be added to the spawn list for each biome that the entity should spawn in. This can be achieved with a [[Biome Modifiers#Add Spawns|&amp;lt;code&amp;gt;forge:add_spawns&amp;lt;/code&amp;gt; biome modifier]].&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Model_JSONs&amp;diff=3333</id>
		<title>Model JSONs</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Model_JSONs&amp;diff=3333"/>
		<updated>2022-09-24T18:20:45Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: Update Wiki according to recent client refactors&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A “model” is simply a shape. It can be a simple cube, it can be several cubes, it can be a truncated icosidodecahedron, or anything in between. Most models you’ll see will be in the vanilla JSON format. Models in other formats are loaded into an &amp;lt;code&amp;gt;IUnbakedGeometry&amp;lt;/code&amp;gt; by an &amp;lt;code&amp;gt;IGeometryLoader&amp;lt;/code&amp;gt; at runtime. Forge provides default implementations for WaveFront OBJ files, buckets, composite models, models in different render layers, and a reimplementation of Vanilla's &amp;lt;code&amp;gt;builtin/generated&amp;lt;/code&amp;gt; item model. Most things do not care about what loaded the model or what format it’s in as they all &amp;quot;bake&amp;quot; into an &amp;lt;code&amp;gt;BakedModel&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
When &amp;lt;code&amp;gt;ResourceLocation&amp;lt;/code&amp;gt; refers to a model, the path is normally relative to &amp;lt;code&amp;gt;models&amp;lt;/code&amp;gt; (e.g. &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;examplemod:block/block&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; → &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;assets/examplemod/models/block/block&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
Block and item models differ in a few ways, the major one being [[Item Overrides|item property overrides]].&lt;br /&gt;
&lt;br /&gt;
== Textures ==&lt;br /&gt;
Textures, like models, are contained within resource packs and are referred to with &amp;lt;code&amp;gt;ResourceLocation&amp;lt;/code&amp;gt;s. When &amp;lt;code&amp;gt;ResourceLocation&amp;lt;/code&amp;gt;s refer to textures in models, the paths are taken to be relative to &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;textures/&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; (e.g. &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;examplemod:blocks/test&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; → &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;assets/examplemod/textures/blocks/test.png&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;). Additionally, in Minecraft, the [https://en.wikipedia.org/wiki/UV_mapping UV coordinates] (0,0) are taken to mean the ''&amp;lt;code&amp;gt;top-left&amp;lt;/code&amp;gt;'' corner. UVs are &amp;lt;code&amp;gt;always&amp;lt;/code&amp;gt; from 0 to 16. If a texture is larger or smaller, the coordinates are scaled to fit. A texture should also be square, and the side length of a texture should be a power of two, as doing otherwise breaks mipmapping. (E.g. 1x1, 2x2, 8x8, 16x16, and 128x128 are good. 5x5 and 30x30 are not recommended because they are not powers of 2. 5x10 and 4x8 are completely broken as they are not square.) If there is an &amp;lt;code&amp;gt;mcmeta&amp;lt;/code&amp;gt; file associated with the texture, and an animation is defined, the image can be rectangular and is interpreted as a vertical sequence of square regions from top to bottom, where each square is a frame of the animation.&lt;br /&gt;
&lt;br /&gt;
== JSON Models ==&lt;br /&gt;
Vanilla Minecraft’s JSON model format is rather simple. It defines cuboid (cube/rectangular prism) elements, and assigns textures to their faces. On the [https://minecraft.fandom.com/wiki/Model#Block_models wiki], there is a definition of its format.&lt;br /&gt;
&lt;br /&gt;
{{Colored box|title=Tip|content=JSON models only support cuboid elements; there is no way to express a triangular wedge or anything like it. To have more complicated models, another format must be used.}}&lt;br /&gt;
&lt;br /&gt;
When a &amp;lt;code&amp;gt;ResourceLocation&amp;lt;/code&amp;gt; refers to the location of a JSON model, it is not suffixed with &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;.json&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;, unlike OBJ (e.g. &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;minecraft:block/cube_all&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;, not &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;minecraft:block/cube_all.json&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
== WaveFront OBJ Models ==&lt;br /&gt;
Forge adds a loader for the &amp;lt;code&amp;gt;.obj&amp;lt;/code&amp;gt; file format. To use these models, the JSON must reference the &amp;lt;code&amp;gt;forge:obj&amp;lt;/code&amp;gt; loader. This loader accepts any model location that is in a registered namespace and whose path ends in &amp;lt;code&amp;gt;.obj&amp;lt;/code&amp;gt;. The &amp;lt;code&amp;gt;.mtl&amp;lt;/code&amp;gt; file should be placed in the same location with the same name as the &amp;lt;code&amp;gt;.obj&amp;lt;/code&amp;gt; to be used automatically. The &amp;lt;code&amp;gt;.mtl&amp;lt;/code&amp;gt; file will probably have to be manually edited to change the paths pointing to textures defined within the JSON. Additionally, the V axis for textures may be flipped depending on the external program that created the model (i.e. V = 0 may be the bottom edge, not the top). This may be rectified in the modelling program itself or done in the model JSON like so:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;json&amp;quot;&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
  &amp;quot;__comment&amp;quot;: &amp;quot;Add the following line on the same level as a 'model' declaration.&amp;quot;,&lt;br /&gt;
  &amp;quot;loader&amp;quot;: &amp;quot;forge:obj&amp;quot;,&lt;br /&gt;
  &amp;quot;flip-v&amp;quot;: true,&lt;br /&gt;
  &amp;quot;model&amp;quot;: &amp;quot;examplemod:models/block/model.obj&amp;quot;,&lt;br /&gt;
  &amp;quot;textures&amp;quot;: {&lt;br /&gt;
    &amp;quot;_comment&amp;quot;: &amp;quot;Can refer to in .mtl using #texture0&amp;quot;,&lt;br /&gt;
    &amp;quot;texture0&amp;quot;: &amp;quot;minecraft:block/dirt&amp;quot;,&lt;br /&gt;
    &amp;quot;particle&amp;quot;: &amp;quot;minecraft:block/dirt&amp;quot;&lt;br /&gt;
  }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Category:Models]]&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Capabilities&amp;diff=3332</id>
		<title>Capabilities</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Capabilities&amp;diff=3332"/>
		<updated>2022-09-24T18:07:56Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''Capabilities''' are a Forge system that allows cross-mod interactions by allowing capability ''providers'' to&lt;br /&gt;
dynamically respect contracts and provide specialized behavior without requiring the implementation of many interfaces&lt;br /&gt;
or hard dependencies on mods.&lt;br /&gt;
&lt;br /&gt;
== History ==&lt;br /&gt;
In an ideal world, all that would be needed for a mod to provide the equivalent of a capability would be implementing an&lt;br /&gt;
interface. This is in fact how cross-mod interaction used to work prior to the introduction of capabilities.&lt;br /&gt;
&lt;br /&gt;
The real world, though, is often much more complicated: users wanted to be free to combine mods the way they wanted and&lt;br /&gt;
saw fit, and developers wanted to be able to declare ''soft'' dependencies on other mods, thus reducing the need of&lt;br /&gt;
having a huge mod pack just for testing.&lt;br /&gt;
&lt;br /&gt;
The first approach used by Forge was conditional stripping of interfaces and methods, but this proved to be problematic.&lt;br /&gt;
While the idea works well in theory, in practice the ASM editing of classes relied on complex mechanics and could lead&lt;br /&gt;
to hard to spot bugs.&lt;br /&gt;
&lt;br /&gt;
For this reason, the entire system was redesigned and the concept of '''capabilities''' was born.&lt;br /&gt;
&lt;br /&gt;
== The Concept ==&lt;br /&gt;
A capability allows any capability provider to conditionally expose a certain ability to do something, e.g. accepting&lt;br /&gt;
power or handling items. A capability provider, moreover, can decide to expose a capability only on certain sides,&lt;br /&gt;
allowing for easy interactions with hoppers, cables, etc.&lt;br /&gt;
&lt;br /&gt;
Capabilities may also be added and removed dynamically both from the &amp;quot;owner&amp;quot; of the capability provider and other mods,&lt;br /&gt;
allowing even easier cross-mod interaction. For example, a mod that isn't compatible with Forge Energy could be&lt;br /&gt;
converted into one by dynamically attaching the Forge Energy capability and handling the conversion to a third-party&lt;br /&gt;
energy system without having to alter the original mod.&lt;br /&gt;
&lt;br /&gt;
== Terminology ==&lt;br /&gt;
The high flexibility of the system comes with a cost, though, which is terminology. The following section wants to be a&lt;br /&gt;
dictionary of sorts, defining all the terms that you may come across when dealing with capabilities.&lt;br /&gt;
&lt;br /&gt;
In the rest of this article, we will refer to these terms frequently, so make sure you are familiar with them.&lt;br /&gt;
&lt;br /&gt;
; Capability&lt;br /&gt;
: the ability to perform something. In-code this is represented by the &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; class.&lt;br /&gt;
; Capability Provider&lt;br /&gt;
: something that is able to support capabilities and provides a mean of accessing them. In-code they are represented by implementations of &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt;. There are multiple kinds of capability providers:&lt;br /&gt;
:; Volatile Provider&lt;br /&gt;
:: a provider that doesn't persist data to disk; once the provider ceases to exist for any number of reasons, all capability data gets deleted.&lt;br /&gt;
:; Persistent Provider&lt;br /&gt;
:: a provider that requires all capabilities to serialize data to disk, in order to persist data even across game restarts. They implement the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
:; Agnostic Provider&lt;br /&gt;
:: a provider that isn't neither volatile nor persistent, rather delegates the decision either to the capability directly or to sub-implementations. They also implement the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
; Capability Interface&lt;br /&gt;
: the interface that defines the contract of the capability, so what operations the capability exposes.&lt;br /&gt;
; Capability Implementation&lt;br /&gt;
: one of the possibly many implementations of the capability interface, that actually carries out the work.&lt;br /&gt;
&lt;br /&gt;
The wary reader may note that both ''persistent'' and ''agnostic'' providers are represented the same way in code. In&lt;br /&gt;
fact, the only difference between them comes from pure semantics in how their serialization methods are designed. This&lt;br /&gt;
will be further discussed in their respective sections.&lt;br /&gt;
&lt;br /&gt;
Moreover, it is also common to refer to the capability interface as simply the ''capability''. While not strictly&lt;br /&gt;
correct, due to common usage we will also use this convention. So, to refer to the capability interface&lt;br /&gt;
&amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt;, we will usually talk about the &amp;quot;&amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt; capability&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Forge-provided Capabilities and Providers ==&lt;br /&gt;
In order to ensure mods can work together seamlessly, Forge provides a set of default capabilities and capability&lt;br /&gt;
providers.&lt;br /&gt;
&lt;br /&gt;
The default capability providers in a Forge environment are: &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;,&lt;br /&gt;
&amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;Level&amp;lt;/code&amp;gt;, and &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt;. These are all agnostic providers, since they don't&lt;br /&gt;
mandate any sort of capability persistency requirements. Rather, it is the job of whoever subclasses these providers to&lt;br /&gt;
deal with either volatile or non-volatile capabilities.&lt;br /&gt;
&lt;br /&gt;
The default capabilities that forge provides are represented by the interfaces &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt;,&lt;br /&gt;
&amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;IFluidHandlerItem&amp;lt;/code&amp;gt;, and &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt;. Each one of these capabilities will be discussed in the corresponding section.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IItemHandler&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to have some sort of internal&lt;br /&gt;
'''inventory''' with a certain number of slots, from which items can be inserted and extracted. It is also possible,&lt;br /&gt;
though, to expose this capability even if no such inventory is present as long as the capability provider can emulate&lt;br /&gt;
its presence (e.g. tools that allow accessing remote inventories).&lt;br /&gt;
&lt;br /&gt;
This effectively '''replaces''' the vanilla interfaces &amp;lt;code&amp;gt;Container&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;WorldlyContainer&amp;lt;/code&amp;gt;. These&lt;br /&gt;
interfaces are in fact retained only to allow vanilla code to compile and should not be used in mod code. This extends&lt;br /&gt;
to anything that implements those vanilla interfaces, such as &amp;lt;code&amp;gt;RandomizableContainerBlockEntity&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;ItemStackHandler&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IFluidHandler&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to handle and store fluids&lt;br /&gt;
in one or multiple fluid tanks. It is effectively the equivalent in terms of fluids of the &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt;&lt;br /&gt;
capability.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;TileFluidHandler&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IFluidHandlerItem&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IFluidHandlerItem&amp;lt;/code&amp;gt; capability refers to the ability for an &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt; capability provider&lt;br /&gt;
to handle and store fluids in one or multiple fluid tanks. It is basically a specialized version of the&lt;br /&gt;
&amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt; capability that allows &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;s to define a custom container.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IEnergyStorage&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to store, consume, and&lt;br /&gt;
produce energy. This capability is the base capability for what's commonly known in the modded world as Forge Energy (or&lt;br /&gt;
FE), i.e. the energy system most mods use. Its internal design is heavily based on the (now defunct) Redstone Flux&lt;br /&gt;
Energy API, supporting both a push and pull system.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;EnergyStorage&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Working with Capabilities ==&lt;br /&gt;
&lt;br /&gt;
Both capability providers and users need to be able to provide and access capabilities through a common framework,&lt;br /&gt;
otherwise the ideal of dynamic and mod-agnostic would not really exist. For this reason, both capability providers and&lt;br /&gt;
capability ''accessors'' (which we define as everything that wants to access a capability), also known as '''clients''' or '''users''',&lt;br /&gt;
need to work together and with Forge to ensure that the common interface is used sensibly and correctly by all parties.&lt;br /&gt;
&lt;br /&gt;
=== Obtaining a Capability ===&lt;br /&gt;
&lt;br /&gt;
Before being able to work with a capability, it is necessary to obtain an instance of the &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; object itself.&lt;br /&gt;
&lt;br /&gt;
A &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; can obtained at any time using &amp;lt;code&amp;gt;CapabilityManager#get&amp;lt;/code&amp;gt;. This takes in an anonymous &amp;lt;code&amp;gt;CapabilityToken&amp;lt;/code&amp;gt; to still allow for a soft dependency system while also keeping hold of any generic information needed. As such, you can always obtain a non-null capability.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
public static Capability&amp;lt;IItemHandler&amp;gt; ITEM_HANDLER = CapabilityManager.get(new CapabilityToken&amp;lt;&amp;gt;(){});&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The above code will let Forge know that the field &amp;lt;code&amp;gt;ITEM_HANDLER&amp;lt;/code&amp;gt; should be analogous with the &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability. Note that this does not mean the capability is accessible or registered. To check if it is, call &amp;lt;code&amp;gt;Capability#isRegistered&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
This is, for obvious reasons, redundant, since all capabilities are available through&lt;br /&gt;
&amp;lt;code&amp;gt;ForgeCapabilities&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== Exposing a Capability ===&lt;br /&gt;
&lt;br /&gt;
Exposing a capability is a voluntary act by a capability provider that allows the capability to be discovered and&lt;br /&gt;
accessed by users.&lt;br /&gt;
&lt;br /&gt;
To do so, a capability provider needs to juggle a couple more moving pieces to ensure that the capability state remains&lt;br /&gt;
consistent and that the lookup remains fast. It is in fact possible for a capability provider to be asked to provide&lt;br /&gt;
many capabilities many times in the same tick. For this reason, a provider is asked to do the following:&lt;br /&gt;
&lt;br /&gt;
* the &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt;s that get returned '''must be cached''';&lt;br /&gt;
* if a capability changes exposure state (more on this later), all listeners '''must be notified''';&lt;br /&gt;
* if a capability gets invalidated (more on this later), all listeners '''must be notified'''&lt;br /&gt;
* the lookup inside &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; must be performed with '''an &amp;lt;code&amp;gt;if&amp;lt;/code&amp;gt;-&amp;lt;code&amp;gt;else&amp;lt;/code&amp;gt; chain''';&lt;br /&gt;
* all unexposed but still present capabilities '''should be available''' if the provider is queried with a &amp;lt;code&amp;gt;null&amp;lt;/code&amp;gt; direction (see ''Accessing a Capability'' for more information);&lt;br /&gt;
* if no capability of a given type is available or accessible, the provider '''must call &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt; as long as it is possible to do so'''.&lt;br /&gt;
&lt;br /&gt;
Capability providers must also reflect changes in the ''exposure state'' of a capability, meaning that if the&lt;br /&gt;
accessibility of a capability from a certain &amp;lt;code&amp;gt;Direction&amp;lt;/code&amp;gt; changes (refer to&lt;br /&gt;
[[#Accessing a Capability|Accessing a Capability]] for more information), it is the provider's responsibility to trigger&lt;br /&gt;
a state response by invalidating the returned &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; and caching a new one. This should also be&lt;br /&gt;
performed when a capability gets ''invalidated'', such as when a capability provider gets removed.&lt;br /&gt;
&lt;br /&gt;
With all of the above in mind, part of a capability provider implementation may be similar to the following snippet:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
// suppose the presence of a field 'inventory' of type 'IItemHandler'&lt;br /&gt;
&lt;br /&gt;
private LazyOptional&amp;lt;IItemhandler&amp;gt; inventoryOptional = LazyOptional.empty();&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; capability, @Nullable Direction direction) {&lt;br /&gt;
    if (capability == ForgeCapabilities.ITEM_HANDLER&lt;br /&gt;
            &amp;amp;&amp;amp; (direction == null || direction == Direction.UP || direction == Direction.DOWN)) {&lt;br /&gt;
        return this.inventoryOptional.cast();&lt;br /&gt;
    }&lt;br /&gt;
    return super.getCapability(capability, direction); // See note after snippet&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
public void invalidateCaps()&lt;br /&gt;
{&lt;br /&gt;
    this.inventoryOptional = LazyOptional.of(() -&amp;gt; this.inventory);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
protected void invalidateCaps() {&lt;br /&gt;
    super.invalidateCaps();&lt;br /&gt;
    this.inventoryOptional.invalidate();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This possible implementation of a capability provider exposes an &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability and restricts&lt;br /&gt;
access only to the &amp;lt;code&amp;gt;UP&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;DOWN&amp;lt;/code&amp;gt; directions. If we assume this capability provider is a&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, then we may also say that the inventory is only accessible from the top and the bottom of the&lt;br /&gt;
block.&lt;br /&gt;
&lt;br /&gt;
Moreover, the capability gets automatically invalidated when the provider gets invalidated. Assuming this is a&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, this usually happens when the block gets removed from the level or unloaded due to distance.&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt; call at the end of the &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; method is extremely important, since it's what&lt;br /&gt;
allows Attaching external Capabilities to capability providers. Nevertheless, it is not always possible to invoke&lt;br /&gt;
&amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt;: in those cases, an empty &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; should be returned.&lt;br /&gt;
&lt;br /&gt;
=== Attaching a Capability ===&lt;br /&gt;
&lt;br /&gt;
Attaching a Capability is a process by which external agents &amp;quot;modify&amp;quot; a Capability Provider, making it expose additional&lt;br /&gt;
capabilities other than the already available ones.&lt;br /&gt;
&lt;br /&gt;
To do so, the '''attaching agent''' (which means the thing that wants to attach a capability to another provider) must&lt;br /&gt;
listen to the &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;T&amp;amp;gt;&amp;lt;/code&amp;gt;. The &amp;lt;code&amp;gt;T&amp;lt;/code&amp;gt; in this case represents the capability&lt;br /&gt;
provider you want to attach the capability to. Note that the type of &amp;lt;code&amp;gt;T&amp;lt;/code&amp;gt; '''must''' be the base type of the&lt;br /&gt;
capability provider, not a subclass. As an example, if you want to attach a capability to a &amp;lt;code&amp;gt;MyBlockEntity&amp;lt;/code&amp;gt;,&lt;br /&gt;
which extends &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, you'll have to listen to &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;BlockEntity&amp;amp;gt;&amp;lt;/code&amp;gt;,&lt;br /&gt;
'''NOT''' to &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;MyBlockEntity&amp;amp;gt;&amp;lt;/code&amp;gt;, since the latter will never fire.&lt;br /&gt;
&lt;br /&gt;
The attaching agent can use the provided methods &amp;lt;code&amp;gt;getObject&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;addCapability&amp;lt;/code&amp;gt;, and &lt;br /&gt;
&amp;lt;code&amp;gt;addListener&amp;lt;/code&amp;gt; to check whether the capability should be attached to the current object and perform the&lt;br /&gt;
desired action.&lt;br /&gt;
&lt;br /&gt;
When attaching a capability, the attaching agent should also provide a name in the form of a&lt;br /&gt;
&amp;lt;code&amp;gt;ResourceLocation&amp;lt;/code&amp;gt;. The name '''must''' be under the attaching agent's namespace, but no restrictions are&lt;br /&gt;
placed on the actual name, as long as it is unique inside the given namespace.&lt;br /&gt;
&lt;br /&gt;
Maybe a little counter-intuitively, the process of attaching does not attach a capability nor a capability interface&lt;br /&gt;
directly. Rather, the attaching agent should create its own implementation of a '''Capability Provider''' and attach it&lt;br /&gt;
via the event. This is done so that the attaching agent can have control over when, how, and where its capabilities are&lt;br /&gt;
exposed, instead of relying on the game itself deciding these parameters. For this reason, all considerations given in&lt;br /&gt;
the [[#Exposing a Capability|Exposing a Capability]] section on how to correctly create a Capability Provider.&lt;br /&gt;
&lt;br /&gt;
With the above in mind, part of an attaching agent may be similar to the following snippet of code:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void onAttachingCapabilities(final AttachCapabilitiesEvent&amp;lt;BlockEntity&amp;gt; event) {&lt;br /&gt;
    if (!(event.getObject() instanceof EnergyBasedBlockEntity)) return;&lt;br /&gt;
&lt;br /&gt;
    EnergyStorage backend = new EnergyStorage(((EnergyBasedBlockEntity) event.getObject()).capacity);&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; optionalStorage = LazyOptional.of(() -&amp;gt; backend);&lt;br /&gt;
&lt;br /&gt;
    ICapabilityProvider provider = new ICapabilityProvider() {&lt;br /&gt;
        @Override&lt;br /&gt;
        public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; cap, @Nullable Direction direction) {&lt;br /&gt;
            if (cap == ForgeCapabilities.ENERGY) {&lt;br /&gt;
                return optionalStorage.cast();&lt;br /&gt;
            }&lt;br /&gt;
            return LazyOptional.empty();&lt;br /&gt;
        }&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    event.addCapability(new ResourceLocation(&amp;quot;examplemod&amp;quot;, &amp;quot;fe_compatibility&amp;quot;), provider);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This example implementation of an attaching agent attaches a &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability to all&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; instance that are a subclass of &amp;lt;code&amp;gt;EnergyBasedBlockEntity&amp;lt;/code&amp;gt;. It also sets up the&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; for invalidation if the parent capability provider gets invalidated.&lt;br /&gt;
&lt;br /&gt;
Note also the call of &amp;lt;code&amp;gt;LazyOptional.empty()&amp;lt;/code&amp;gt; rather than a &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt;. This is needed because when&lt;br /&gt;
attaching a capability, the parent capability provider isn't known. For this reason, it is necessary to return an empty&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt;. The game will then handle automatic merging of the various different providers into a single&lt;br /&gt;
one.&lt;br /&gt;
&lt;br /&gt;
The above example is one of a '''Volatile''' Capability Provider. On the other hand, mods may want to persist their&lt;br /&gt;
data across sessions. In this case, they should attach a '''Persistent''' Capability Provider: this can be done either&lt;br /&gt;
by implementing the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface along with &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt; or by&lt;br /&gt;
implementing the &amp;lt;code&amp;gt;ICapabilitySerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
&lt;br /&gt;
The previous example reworked to use a Persistent Capability Provider may be similar to the following snippet:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void onAttachingCapabilities(final AttachCapabilitiesEvent&amp;lt;BlockEntity&amp;gt; event) {&lt;br /&gt;
    if (!(event.getObject() instanceof EnergyBasedBlockEntity)) return;&lt;br /&gt;
&lt;br /&gt;
    EnergyStorage backend = new EnergyStorage(((EnergyBasedBlockEntity) event.getObject()).capacity);&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; optionalStorage = LazyOptional.of(() -&amp;gt; backend);&lt;br /&gt;
    Capability&amp;lt;IEnergyStorage&amp;gt; capability = ForgeCapabilities.ENERGY;&lt;br /&gt;
&lt;br /&gt;
    ICapabilityProvider provider = new ICapabilitySerializable&amp;lt;IntTag&amp;gt;() {&lt;br /&gt;
        @Override&lt;br /&gt;
        public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; cap, @Nullable Direction direction) {&lt;br /&gt;
            if (cap == capability) {&lt;br /&gt;
                return optionalStorage.cast();&lt;br /&gt;
            }&lt;br /&gt;
            return LazyOptional.empty();&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @Override&lt;br /&gt;
        public IntTag serializeNBT() {&lt;br /&gt;
            return backend.serializeNBT();&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @Override&lt;br /&gt;
        public void deserializeNBT(IntTag tag) {&lt;br /&gt;
            backend.deserializeNBT(tag);&lt;br /&gt;
        }&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    event.addCapabilities(new ResourceLocation(&amp;quot;examplemod&amp;quot;, &amp;quot;fe_compatibility&amp;quot;), provider);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that when using capabilities on entities, you should manually invalidate the capability via &amp;lt;code&amp;gt;invalidateCaps()&amp;lt;/code&amp;gt;, via etc. &amp;lt;code&amp;gt;PlayerEvent.Clone&amp;lt;/code&amp;gt;. This is due to the fact that players are recreated &amp;amp; copied when moving across dimensions, not simply moved.&lt;br /&gt;
&lt;br /&gt;
=== Accessing a Capability ===&lt;br /&gt;
&lt;br /&gt;
Accessing a Capability is the process by which a user is able to '''query''' a Capability Provider for a specific&lt;br /&gt;
instance of a capability.&lt;br /&gt;
&lt;br /&gt;
This is perhaps the second most important part of the entire capability system, since it is what allows cross-mod&lt;br /&gt;
interaction. To obtain an instance of a Capability, the user must first get a hold of the Capability Provider that&lt;br /&gt;
should be queried. This can be done in a variety of ways and is outside the scope of this article. The user should&lt;br /&gt;
then invoke the &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; method passing the unique instance of the capability that should be queried&lt;br /&gt;
(see [[#Obtaining a Capability|Obtaining a Capability]] for more information) and the querying &amp;lt;code&amp;gt;Direction&amp;lt;/code&amp;gt;,&lt;br /&gt;
if applicable.&lt;br /&gt;
&lt;br /&gt;
The returned object is a &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; wrapping the queried Capability, if the capability provider exposes&lt;br /&gt;
it, otherwise it will be empty. The &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; can be either unwrapped via an &amp;lt;code&amp;gt;orElse&amp;lt;/code&amp;gt; or&lt;br /&gt;
used directly via &amp;lt;code&amp;gt;ifPresent&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
It is '''highly suggested''' to cache the returned &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; to avoid querying the same provider every&lt;br /&gt;
time, in order to improve performance. The user should thus register itself to the invalidation listener via the&lt;br /&gt;
&amp;lt;code&amp;gt;addListener&amp;lt;/code&amp;gt; method. This ensures that the user will be able to react to the invalidation of the&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; and remove it from the cache.&lt;br /&gt;
&lt;br /&gt;
With the above in mind, part of an user may be similar to the following snippet of code:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
// note the use of EnumMap, which is much more performant than HashMap for enum keys&lt;br /&gt;
private final Map&amp;lt;Direction, LazyOptional&amp;lt;IEnergyStorage&amp;gt;&amp;gt; cache = new EnumMap&amp;lt;&amp;gt;(Direction.class);&lt;br /&gt;
&lt;br /&gt;
private void sendPowerTo(int power, Direction direction) {&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; targetCapability = cache.get(direction);&lt;br /&gt;
&lt;br /&gt;
    if (targetCapability == null) {&lt;br /&gt;
        ICapabilityProvider provider = level.getBlockEntity(pos.relative(direction));&lt;br /&gt;
        targetCapability = provider.getCapability(ForgeCapabilities.ENERGY, direction.getOpposite());&lt;br /&gt;
        cache.put(direction, targetCapability);&lt;br /&gt;
        targetCapability.addListener(self -&amp;gt; cache.put(direction, null));&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    targetCapability.ifPresent(storage -&amp;gt; storage.receiveEnergy(power, false));&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This example implementation of an user is querying via a &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; the neighboring capability provider&lt;br /&gt;
for an &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability. Before obtaining the provider, the code performs a cache lookup for the&lt;br /&gt;
targeted capability. If the check succeeds, then no lookup is performed; if the check fails, the targeted Capability&lt;br /&gt;
Provider is obtained and queried for the Capability. The obtained &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; is then cached and a&lt;br /&gt;
listener is attached to it so that the cache would be emptied on invalidation. The code then continues with the&lt;br /&gt;
interaction with the capability, which is outside the scope of this article.&lt;br /&gt;
&lt;br /&gt;
== Creating Custom Capabilities ==&lt;br /&gt;
&lt;br /&gt;
While the various capabilities provided by Forge may satisfy the most common use cases, there is always the chance that&lt;br /&gt;
a mod may require a custom solution. For this reason, Forge provides a way to define a custom Capability.&lt;br /&gt;
&lt;br /&gt;
Defining a custom Capability requires the user to provide one main component: the Capability Interface. Optionally, a &lt;br /&gt;
Capability Implementation and Capability Provider can also be created. In this&lt;br /&gt;
case, the provider will be used as described in [[#Attaching a Capability|Attaching a Capability]]. The various details &lt;br /&gt;
for all these components are described in the respective sections of this article.&lt;br /&gt;
&lt;br /&gt;
In this section, we will refer to the implementation of a &amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt; capability, that can be used to&lt;br /&gt;
store a single mutable &amp;lt;code&amp;gt;String&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Refer also to [[#Code Examples|Code Examples]] for an example on how the various components may be implemented in a&lt;br /&gt;
real-world scenario.&lt;br /&gt;
&lt;br /&gt;
=== The Capability Interface and the Capability Implementation ===&lt;br /&gt;
&lt;br /&gt;
The Capability Interface is one of the most important parts of a Capability: without it, the Capability effectively does&lt;br /&gt;
not exist. Designing a Capability Interface is exactly like designing any Java interface, so the particular details will&lt;br /&gt;
be glossed over in this section.&lt;br /&gt;
&lt;br /&gt;
The Capability Implementation, on the other hand, is the implementation of the previously defined Capability Interface.&lt;br /&gt;
Usual rules for interface implementations follow. There can be more than one Capability Implementation for each&lt;br /&gt;
capability. &lt;br /&gt;
&lt;br /&gt;
Note that a '''well-formed''' capability implementation should '''not store''' the Capability Provider inside of it: we&lt;br /&gt;
call the capability implementation ''provider-agnostic''. This is not a hard-requirement, though, rather it should act&lt;br /&gt;
more as a guideline. There are in fact certain situations where this cannot be avoided (e.g. attaching a client-synced&lt;br /&gt;
capability to an &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
Given all of the above information, this may be an example implementation of both a Capability Interface and a&lt;br /&gt;
Capability Implementation:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@AutoRegisterCapability // This annotation registers the capability for you automatically!&lt;br /&gt;
public interface MyCapability {&lt;br /&gt;
    String getValue();&lt;br /&gt;
    void setValue(String value);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
public class MyCapabilityImplementation implements MyCapability {&lt;br /&gt;
    private String value;&lt;br /&gt;
&lt;br /&gt;
    @Override&lt;br /&gt;
    public String getValue() {&lt;br /&gt;
        return this.value;&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    @Override&lt;br /&gt;
    public void setValue(String value) {&lt;br /&gt;
        this.value = value;&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that in this case, only a single implementation is provided.&lt;br /&gt;
&lt;br /&gt;
=== The Capability Provider ===&lt;br /&gt;
&lt;br /&gt;
The Capability Provider is an optional component of the capability that allows the Capability to be attached to a&lt;br /&gt;
component. The details on how a Capability Provider should behave have already been discussed in the two previous&lt;br /&gt;
sections [[#Exposing a Capability|Exposing a Capability]] and [[#Attaching a Capability|Attaching a Capability]]: refer&lt;br /&gt;
to those for more information.&lt;br /&gt;
&lt;br /&gt;
=== Class Diagram ===&lt;br /&gt;
&lt;br /&gt;
[[File:Custom Capability Class Diagram.svg|800px|thumb|center|Custom Capability Class Diagram]]&lt;br /&gt;
&lt;br /&gt;
In the above diagram the green and red marked areas are classes from Minecraft and Forge respectively. The classes inside the purple area are only needed if you want to [[#Attaching a Capability|Attach a Capability]]. Furthermore this diagram models a persistent provider and its most basic form, for more information on how to create a more complex provider see [[#Custom Capability Providers|Custom Capability Providers]]. To create a volatile provider instead just do not implement &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Custom Capability Providers ==&lt;br /&gt;
&lt;br /&gt;
Much like custom Capabilities, Forge also allows the creation of custom Capability Providers. The main advantage of this&lt;br /&gt;
is allowing mods to create custom providers for their custom objects, in order to promote not only cross-mod&lt;br /&gt;
compatibility, but also uniformity in the way users may interact with different mod APIs.&lt;br /&gt;
&lt;br /&gt;
This section will only give the basic outline of what is necessary to implement a custom Capability Provider: for more&lt;br /&gt;
in-depth explanation, people are referred to the game code.&lt;br /&gt;
&lt;br /&gt;
By definition, a custom Capability Provider is everything that implements the &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt;&lt;br /&gt;
interface. In this section, though, we will only cover people that may want to replicate the functionality of one of&lt;br /&gt;
the default providers, such as &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; or &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
The easiest way of doing this is extending the &amp;lt;code&amp;gt;CapabilityProvider&amp;lt;/code&amp;gt; class provided by Forge. This will&lt;br /&gt;
automatically set up an ''agnostic'' Capability Provider. To fully initialize the capability provider, the subclass&lt;br /&gt;
should then invoke the &amp;lt;code&amp;gt;gatherCapabilities&amp;lt;/code&amp;gt; method as the last instruction in its constructor, to ensure that&lt;br /&gt;
the game is able to recollect and attach all capabilities that other mods may want to attach to the capability provider.&lt;br /&gt;
&lt;br /&gt;
== Code Examples ==&lt;br /&gt;
&lt;br /&gt;
* [https://gist.github.com/TheCurle/6db954d680f6f067dcdc791355c32c89 A Gist showing a quick and dirty example on how to implement a Capability effectively]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Category:Data Storage]]&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Capabilities&amp;diff=3331</id>
		<title>Capabilities</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Capabilities&amp;diff=3331"/>
		<updated>2022-09-24T18:06:20Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: /* The Capability Interface and the Capability Implementation */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''Capabilities''' are a Forge system that allows cross-mod interactions by allowing capability ''providers'' to&lt;br /&gt;
dynamically respect contracts and provide specialized behavior without requiring the implementation of many interfaces&lt;br /&gt;
or hard dependencies on mods.&lt;br /&gt;
&lt;br /&gt;
== History ==&lt;br /&gt;
In an ideal world, all that would be needed for a mod to provide the equivalent of a capability would be implementing an&lt;br /&gt;
interface. This is in fact how cross-mod interaction used to work prior to the introduction of capabilities.&lt;br /&gt;
&lt;br /&gt;
The real world, though, is often much more complicated: users wanted to be free to combine mods the way they wanted and&lt;br /&gt;
saw fit, and developers wanted to be able to declare ''soft'' dependencies on other mods, thus reducing the need of&lt;br /&gt;
having a huge mod pack just for testing.&lt;br /&gt;
&lt;br /&gt;
The first approach used by Forge was conditional stripping of interfaces and methods, but this proved to be problematic.&lt;br /&gt;
While the idea works well in theory, in practice the ASM editing of classes relied on complex mechanics and could lead&lt;br /&gt;
to hard to spot bugs.&lt;br /&gt;
&lt;br /&gt;
For this reason, the entire system was redesigned and the concept of '''capabilities''' was born.&lt;br /&gt;
&lt;br /&gt;
== The Concept ==&lt;br /&gt;
A capability allows any capability provider to conditionally expose a certain ability to do something, e.g. accepting&lt;br /&gt;
power or handling items. A capability provider, moreover, can decide to expose a capability only on certain sides,&lt;br /&gt;
allowing for easy interactions with hoppers, cables, etc.&lt;br /&gt;
&lt;br /&gt;
Capabilities may also be added and removed dynamically both from the &amp;quot;owner&amp;quot; of the capability provider and other mods,&lt;br /&gt;
allowing even easier cross-mod interaction. For example, a mod that isn't compatible with Forge Energy could be&lt;br /&gt;
converted into one by dynamically attaching the Forge Energy capability and handling the conversion to a third-party&lt;br /&gt;
energy system without having to alter the original mod.&lt;br /&gt;
&lt;br /&gt;
== Terminology ==&lt;br /&gt;
The high flexibility of the system comes with a cost, though, which is terminology. The following section wants to be a&lt;br /&gt;
dictionary of sorts, defining all the terms that you may come across when dealing with capabilities.&lt;br /&gt;
&lt;br /&gt;
In the rest of this article, we will refer to these terms frequently, so make sure you are familiar with them.&lt;br /&gt;
&lt;br /&gt;
; Capability&lt;br /&gt;
: the ability to perform something. In-code this is represented by the &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; class.&lt;br /&gt;
; Capability Provider&lt;br /&gt;
: something that is able to support capabilities and provides a mean of accessing them. In-code they are represented by implementations of &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt;. There are multiple kinds of capability providers:&lt;br /&gt;
:; Volatile Provider&lt;br /&gt;
:: a provider that doesn't persist data to disk; once the provider ceases to exist for any number of reasons, all capability data gets deleted.&lt;br /&gt;
:; Persistent Provider&lt;br /&gt;
:: a provider that requires all capabilities to serialize data to disk, in order to persist data even across game restarts. They implement the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
:; Agnostic Provider&lt;br /&gt;
:: a provider that isn't neither volatile nor persistent, rather delegates the decision either to the capability directly or to sub-implementations. They also implement the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
; Capability Interface&lt;br /&gt;
: the interface that defines the contract of the capability, so what operations the capability exposes.&lt;br /&gt;
; Capability Implementation&lt;br /&gt;
: one of the possibly many implementations of the capability interface, that actually carries out the work.&lt;br /&gt;
&lt;br /&gt;
The wary reader may note that both ''persistent'' and ''agnostic'' providers are represented the same way in code. In&lt;br /&gt;
fact, the only difference between them comes from pure semantics in how their serialization methods are designed. This&lt;br /&gt;
will be further discussed in their respective sections.&lt;br /&gt;
&lt;br /&gt;
Moreover, it is also common to refer to the capability interface as simply the ''capability''. While not strictly&lt;br /&gt;
correct, due to common usage we will also use this convention. So, to refer to the capability interface&lt;br /&gt;
&amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt;, we will usually talk about the &amp;quot;&amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt; capability&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Forge-provided Capabilities and Providers ==&lt;br /&gt;
In order to ensure mods can work together seamlessly, Forge provides a set of default capabilities and capability&lt;br /&gt;
providers.&lt;br /&gt;
&lt;br /&gt;
The default capability providers in a Forge environment are: &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;,&lt;br /&gt;
&amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;Level&amp;lt;/code&amp;gt;, and &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt;. These are all agnostic providers, since they don't&lt;br /&gt;
mandate any sort of capability persistency requirements. Rather, it is the job of whoever subclasses these providers to&lt;br /&gt;
deal with either volatile or non-volatile capabilities.&lt;br /&gt;
&lt;br /&gt;
The default capabilities that forge provides are represented by the interfaces &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt;,&lt;br /&gt;
&amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;IFluidHandlerItem&amp;lt;/code&amp;gt;, and &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt;. Each one of these capabilities will be discussed in the corresponding section.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IItemHandler&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to have some sort of internal&lt;br /&gt;
'''inventory''' with a certain number of slots, from which items can be inserted and extracted. It is also possible,&lt;br /&gt;
though, to expose this capability even if no such inventory is present as long as the capability provider can emulate&lt;br /&gt;
its presence (e.g. tools that allow accessing remote inventories).&lt;br /&gt;
&lt;br /&gt;
This effectively '''replaces''' the vanilla interfaces &amp;lt;code&amp;gt;Container&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;WorldlyContainer&amp;lt;/code&amp;gt;. These&lt;br /&gt;
interfaces are in fact retained only to allow vanilla code to compile and should not be used in mod code. This extends&lt;br /&gt;
to anything that implements those vanilla interfaces, such as &amp;lt;code&amp;gt;RandomizableContainerBlockEntity&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;ItemStackHandler&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IFluidHandler&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to handle and store fluids&lt;br /&gt;
in one or multiple fluid tanks. It is effectively the equivalent in terms of fluids of the &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt;&lt;br /&gt;
capability.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;TileFluidHandler&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IFluidHandlerItem&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IFluidHandlerItem&amp;lt;/code&amp;gt; capability refers to the ability for an &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt; capability provider&lt;br /&gt;
to handle and store fluids in one or multiple fluid tanks. It is basically a specialized version of the&lt;br /&gt;
&amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt; capability that allows &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;s to define a custom container.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IEnergyStorage&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to store, consume, and&lt;br /&gt;
produce energy. This capability is the base capability for what's commonly known in the modded world as Forge Energy (or&lt;br /&gt;
FE), i.e. the energy system most mods use. Its internal design is heavily based on the (now defunct) Redstone Flux&lt;br /&gt;
Energy API, supporting both a push and pull system.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;EnergyStorage&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Working with Capabilities ==&lt;br /&gt;
&lt;br /&gt;
Both capability providers and users need to be able to provide and access capabilities through a common framework,&lt;br /&gt;
otherwise the ideal of dynamic and mod-agnostic would not really exist. For this reason, both capability providers and&lt;br /&gt;
capability ''accessors'' (which we define as everything that wants to access a capability), also known as '''clients''' or '''users''',&lt;br /&gt;
need to work together and with Forge to ensure that the common interface is used sensibly and correctly by all parties.&lt;br /&gt;
&lt;br /&gt;
=== Obtaining a Capability ===&lt;br /&gt;
&lt;br /&gt;
Before being able to work with a capability, it is necessary to obtain an instance of the &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; object itself.&lt;br /&gt;
&lt;br /&gt;
A &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; can obtained at any time using &amp;lt;code&amp;gt;CapabilityManager#get&amp;lt;/code&amp;gt;. This takes in an anonymous &amp;lt;code&amp;gt;CapabilityToken&amp;lt;/code&amp;gt; to still allow for a soft dependency system while also keeping hold of any generic information needed. As such, you can always obtain a non-null capability.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
public static Capability&amp;lt;IItemHandler&amp;gt; ITEM_HANDLER = CapabilityManager.get(new CapabilityToken&amp;lt;&amp;gt;(){});&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The above code will let Forge know that the field &amp;lt;code&amp;gt;ITEM_HANDLER&amp;lt;/code&amp;gt; should be analogous with the &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability. Note that this does not mean the capability is accessible or registered. To check if it is, call &amp;lt;code&amp;gt;Capability#isRegistered&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
This is, for obvious reasons, redundant, since all capabilities are available through&lt;br /&gt;
&amp;lt;code&amp;gt;ForgeCapabilities&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== Exposing a Capability ===&lt;br /&gt;
&lt;br /&gt;
Exposing a capability is a voluntary act by a capability provider that allows the capability to be discovered and&lt;br /&gt;
accessed by users.&lt;br /&gt;
&lt;br /&gt;
To do so, a capability provider needs to juggle a couple more moving pieces to ensure that the capability state remains&lt;br /&gt;
consistent and that the lookup remains fast. It is in fact possible for a capability provider to be asked to provide&lt;br /&gt;
many capabilities many times in the same tick. For this reason, a provider is asked to do the following:&lt;br /&gt;
&lt;br /&gt;
* the &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt;s that get returned '''must be cached''';&lt;br /&gt;
* if a capability changes exposure state (more on this later), all listeners '''must be notified''';&lt;br /&gt;
* if a capability gets invalidated (more on this later), all listeners '''must be notified'''&lt;br /&gt;
* the lookup inside &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; must be performed with '''an &amp;lt;code&amp;gt;if&amp;lt;/code&amp;gt;-&amp;lt;code&amp;gt;else&amp;lt;/code&amp;gt; chain''';&lt;br /&gt;
* all unexposed but still present capabilities '''should be available''' if the provider is queried with a &amp;lt;code&amp;gt;null&amp;lt;/code&amp;gt; direction (see ''Accessing a Capability'' for more information);&lt;br /&gt;
* if no capability of a given type is available or accessible, the provider '''must call &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt; as long as it is possible to do so'''.&lt;br /&gt;
&lt;br /&gt;
Capability providers must also reflect changes in the ''exposure state'' of a capability, meaning that if the&lt;br /&gt;
accessibility of a capability from a certain &amp;lt;code&amp;gt;Direction&amp;lt;/code&amp;gt; changes (refer to&lt;br /&gt;
[[#Accessing a Capability|Accessing a Capability]] for more information), it is the provider's responsibility to trigger&lt;br /&gt;
a state response by invalidating the returned &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; and caching a new one. This should also be&lt;br /&gt;
performed when a capability gets ''invalidated'', such as when a capability provider gets removed.&lt;br /&gt;
&lt;br /&gt;
With all of the above in mind, part of a capability provider implementation may be similar to the following snippet:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
// suppose the presence of a field 'inventory' of type 'IItemHandler'&lt;br /&gt;
&lt;br /&gt;
private LazyOptional&amp;lt;IItemhandler&amp;gt; inventoryOptional = LazyOptional.empty();&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; capability, @Nullable Direction direction) {&lt;br /&gt;
    if (capability == ForgeCapabilities.ITEM_HANDLER&lt;br /&gt;
            &amp;amp;&amp;amp; (direction == null || direction == Direction.UP || direction == Direction.DOWN)) {&lt;br /&gt;
        return this.inventoryOptional.cast();&lt;br /&gt;
    }&lt;br /&gt;
    return super.getCapability(capability, direction); // See note after snippet&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
public void invalidateCaps()&lt;br /&gt;
{&lt;br /&gt;
    this.inventoryOptional = LazyOptional.of(() -&amp;gt; this.inventory);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
protected void invalidateCaps() {&lt;br /&gt;
    super.invalidateCaps();&lt;br /&gt;
    this.inventoryOptional.invalidate();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This possible implementation of a capability provider exposes an &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability and restricts&lt;br /&gt;
access only to the &amp;lt;code&amp;gt;UP&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;DOWN&amp;lt;/code&amp;gt; directions. If we assume this capability provider is a&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, then we may also say that the inventory is only accessible from the top and the bottom of the&lt;br /&gt;
block.&lt;br /&gt;
&lt;br /&gt;
Moreover, the capability gets automatically invalidated when the provider gets invalidated. Assuming this is a&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, this usually happens when the block gets removed from the level or unloaded due to distance.&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt; call at the end of the &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; method is extremely important, since it's what&lt;br /&gt;
allows Attaching external Capabilities to capability providers. Nevertheless, it is not always possible to invoke&lt;br /&gt;
&amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt;: in those cases, an empty &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; should be returned.&lt;br /&gt;
&lt;br /&gt;
=== Attaching a Capability ===&lt;br /&gt;
&lt;br /&gt;
Attaching a Capability is a process by which external agents &amp;quot;modify&amp;quot; a Capability Provider, making it expose additional&lt;br /&gt;
capabilities other than the already available ones.&lt;br /&gt;
&lt;br /&gt;
To do so, the '''attaching agent''' (which means the thing that wants to attach a capability to another provider) must&lt;br /&gt;
listen to the &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;T&amp;amp;gt;&amp;lt;/code&amp;gt;. The &amp;lt;code&amp;gt;T&amp;lt;/code&amp;gt; in this case represents the capability&lt;br /&gt;
provider you want to attach the capability to. Note that the type of &amp;lt;code&amp;gt;T&amp;lt;/code&amp;gt; '''must''' be the base type of the&lt;br /&gt;
capability provider, not a subclass. As an example, if you want to attach a capability to a &amp;lt;code&amp;gt;MyBlockEntity&amp;lt;/code&amp;gt;,&lt;br /&gt;
which extends &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, you'll have to listen to &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;BlockEntity&amp;amp;gt;&amp;lt;/code&amp;gt;,&lt;br /&gt;
'''NOT''' to &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;MyBlockEntity&amp;amp;gt;&amp;lt;/code&amp;gt;, since the latter will never fire.&lt;br /&gt;
&lt;br /&gt;
The attaching agent can use the provided methods &amp;lt;code&amp;gt;getObject&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;addCapability&amp;lt;/code&amp;gt;, and &lt;br /&gt;
&amp;lt;code&amp;gt;addListener&amp;lt;/code&amp;gt; to check whether the capability should be attached to the current object and perform the&lt;br /&gt;
desired action.&lt;br /&gt;
&lt;br /&gt;
When attaching a capability, the attaching agent should also provide a name in the form of a&lt;br /&gt;
&amp;lt;code&amp;gt;ResourceLocation&amp;lt;/code&amp;gt;. The name '''must''' be under the attaching agent's namespace, but no restrictions are&lt;br /&gt;
placed on the actual name, as long as it is unique inside the given namespace.&lt;br /&gt;
&lt;br /&gt;
Maybe a little counter-intuitively, the process of attaching does not attach a capability nor a capability interface&lt;br /&gt;
directly. Rather, the attaching agent should create its own implementation of a '''Capability Provider''' and attach it&lt;br /&gt;
via the event. This is done so that the attaching agent can have control over when, how, and where its capabilities are&lt;br /&gt;
exposed, instead of relying on the game itself deciding these parameters. For this reason, all considerations given in&lt;br /&gt;
the [[#Exposing a Capability|Exposing a Capability]] section on how to correctly create a Capability Provider.&lt;br /&gt;
&lt;br /&gt;
With the above in mind, part of an attaching agent may be similar to the following snippet of code:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void onAttachingCapabilities(final AttachCapabilitiesEvent&amp;lt;BlockEntity&amp;gt; event) {&lt;br /&gt;
    if (!(event.getObject() instanceof EnergyBasedBlockEntity)) return;&lt;br /&gt;
&lt;br /&gt;
    EnergyStorage backend = new EnergyStorage(((EnergyBasedBlockEntity) event.getObject()).capacity);&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; optionalStorage = LazyOptional.of(() -&amp;gt; backend);&lt;br /&gt;
&lt;br /&gt;
    ICapabilityProvider provider = new ICapabilityProvider() {&lt;br /&gt;
        @Override&lt;br /&gt;
        public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; cap, @Nullable Direction direction) {&lt;br /&gt;
            if (cap == ForgeCapabilities.ENERGY) {&lt;br /&gt;
                return optionalStorage.cast();&lt;br /&gt;
            }&lt;br /&gt;
            return LazyOptional.empty();&lt;br /&gt;
        }&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    event.addCapability(new ResourceLocation(&amp;quot;examplemod&amp;quot;, &amp;quot;fe_compatibility&amp;quot;), provider);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This example implementation of an attaching agent attaches a &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability to all&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; instance that are a subclass of &amp;lt;code&amp;gt;EnergyBasedBlockEntity&amp;lt;/code&amp;gt;. It also sets up the&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; for invalidation if the parent capability provider gets invalidated.&lt;br /&gt;
&lt;br /&gt;
Note also the call of &amp;lt;code&amp;gt;LazyOptional.empty()&amp;lt;/code&amp;gt; rather than a &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt;. This is needed because when&lt;br /&gt;
attaching a capability, the parent capability provider isn't known. For this reason, it is necessary to return an empty&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt;. The game will then handle automatic merging of the various different providers into a single&lt;br /&gt;
one.&lt;br /&gt;
&lt;br /&gt;
The above example is one of a '''Volatile''' Capability Provider. On the other hand, mods may want to persist their&lt;br /&gt;
data across sessions. In this case, they should attach a '''Persistent''' Capability Provider: this can be done either&lt;br /&gt;
by implementing the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface along with &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt; or by&lt;br /&gt;
implementing the &amp;lt;code&amp;gt;ICapabilitySerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
&lt;br /&gt;
The previous example reworked to use a Persistent Capability Provider may be similar to the following snippet:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void onAttachingCapabilities(final AttachCapabilitiesEvent&amp;lt;BlockEntity&amp;gt; event) {&lt;br /&gt;
    if (!(event.getObject() instanceof EnergyBasedBlockEntity)) return;&lt;br /&gt;
&lt;br /&gt;
    EnergyStorage backend = new EnergyStorage(((EnergyBasedBlockEntity) event.getObject()).capacity);&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; optionalStorage = LazyOptional.of(() -&amp;gt; backend);&lt;br /&gt;
    Capability&amp;lt;IEnergyStorage&amp;gt; capability = ForgeCapabilities.ENERGY;&lt;br /&gt;
&lt;br /&gt;
    ICapabilityProvider provider = new ICapabilitySerializable&amp;lt;IntTag&amp;gt;() {&lt;br /&gt;
        @Override&lt;br /&gt;
        public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; cap, @Nullable Direction direction) {&lt;br /&gt;
            if (cap == capability) {&lt;br /&gt;
                return optionalStorage.cast();&lt;br /&gt;
            }&lt;br /&gt;
            return LazyOptional.empty();&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @Override&lt;br /&gt;
        public IntTag serializeNBT() {&lt;br /&gt;
            return backend.serializeNBT();&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @Override&lt;br /&gt;
        public void deserializeNBT(IntTag tag) {&lt;br /&gt;
            backend.deserializeNBT(tag);&lt;br /&gt;
        }&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    event.addCapabilities(new ResourceLocation(&amp;quot;examplemod&amp;quot;, &amp;quot;fe_compatibility&amp;quot;), provider);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that when using capabilities on entities, you should manually invalidate the capability via &amp;lt;code&amp;gt;invalidateCaps()&amp;lt;/code&amp;gt;, via etc. &amp;lt;code&amp;gt;PlayerEvent.Clone&amp;lt;/code&amp;gt;. This is due to the fact that players are recreated &amp;amp; copied when moving across dimensions, not simply moved.&lt;br /&gt;
&lt;br /&gt;
=== Accessing a Capability ===&lt;br /&gt;
&lt;br /&gt;
Accessing a Capability is the process by which a user is able to '''query''' a Capability Provider for a specific&lt;br /&gt;
instance of a capability.&lt;br /&gt;
&lt;br /&gt;
This is perhaps the second most important part of the entire capability system, since it is what allows cross-mod&lt;br /&gt;
interaction. To obtain an instance of a Capability, the user must first get a hold of the Capability Provider that&lt;br /&gt;
should be queried. This can be done in a variety of ways and is outside the scope of this article. The user should&lt;br /&gt;
then invoke the &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; method passing the unique instance of the capability that should be queried&lt;br /&gt;
(see [[#Obtaining a Capability|Obtaining a Capability]] for more information) and the querying &amp;lt;code&amp;gt;Direction&amp;lt;/code&amp;gt;,&lt;br /&gt;
if applicable.&lt;br /&gt;
&lt;br /&gt;
The returned object is a &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; wrapping the queried Capability, if the capability provider exposes&lt;br /&gt;
it, otherwise it will be empty. The &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; can be either unwrapped via an &amp;lt;code&amp;gt;orElse&amp;lt;/code&amp;gt; or&lt;br /&gt;
used directly via &amp;lt;code&amp;gt;ifPresent&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
It is '''highly suggested''' to cache the returned &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; to avoid querying the same provider every&lt;br /&gt;
time, in order to improve performance. The user should thus register itself to the invalidation listener via the&lt;br /&gt;
&amp;lt;code&amp;gt;addListener&amp;lt;/code&amp;gt; method. This ensures that the user will be able to react to the invalidation of the&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; and remove it from the cache.&lt;br /&gt;
&lt;br /&gt;
With the above in mind, part of an user may be similar to the following snippet of code:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
// note the use of EnumMap, which is much more performant than HashMap for enum keys&lt;br /&gt;
private final Map&amp;lt;Direction, LazyOptional&amp;lt;IEnergyStorage&amp;gt;&amp;gt; cache = new EnumMap&amp;lt;&amp;gt;(Direction.class);&lt;br /&gt;
&lt;br /&gt;
private void sendPowerTo(int power, Direction direction) {&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; targetCapability = cache.get(direction);&lt;br /&gt;
&lt;br /&gt;
    if (targetCapability == null) {&lt;br /&gt;
        ICapabilityProvider provider = level.getBlockEntity(pos.relative(direction));&lt;br /&gt;
        targetCapability = provider.getCapability(ForgeCapabilities.ENERGY, direction.getOpposite());&lt;br /&gt;
        cache.put(direction, targetCapability);&lt;br /&gt;
        targetCapability.addListener(self -&amp;gt; cache.put(direction, null));&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    targetCapability.ifPresent(storage -&amp;gt; storage.receiveEnergy(power, false));&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This example implementation of an user is querying via a &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; the neighboring capability provider&lt;br /&gt;
for an &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability. Before obtaining the provider, the code performs a cache lookup for the&lt;br /&gt;
targeted capability. If the check succeeds, then no lookup is performed; if the check fails, the targeted Capability&lt;br /&gt;
Provider is obtained and queried for the Capability. The obtained &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; is then cached and a&lt;br /&gt;
listener is attached to it so that the cache would be emptied on invalidation. The code then continues with the&lt;br /&gt;
interaction with the capability, which is outside the scope of this article.&lt;br /&gt;
&lt;br /&gt;
== Creating Custom Capabilities ==&lt;br /&gt;
&lt;br /&gt;
While the various capabilities provided by Forge may satisfy the most common use cases, there is always the chance that&lt;br /&gt;
a mod may require a custom solution. For this reason, Forge provides a way to define a custom Capability.&lt;br /&gt;
&lt;br /&gt;
Defining a custom Capability requires the user to provide one main component: the Capability Interface. Optionally, a &lt;br /&gt;
Capability Implementation and Capability Provider can also be created. In this&lt;br /&gt;
case, the provider will be used as described in [[#Attaching a Capability|Attaching a Capability]]. The various details &lt;br /&gt;
for all these components are described in the respective sections of this article.&lt;br /&gt;
&lt;br /&gt;
In this section, we will refer to the implementation of a &amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt; capability, that can be used to&lt;br /&gt;
store a single mutable &amp;lt;code&amp;gt;String&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Refer also to [[#Code Examples|Code Examples]] for an example on how the various components may be implemented in a&lt;br /&gt;
real-world scenario.&lt;br /&gt;
&lt;br /&gt;
=== The Capability Interface and the Capability Implementation ===&lt;br /&gt;
&lt;br /&gt;
The Capability Interface is one of the most important parts of a Capability: without it, the Capability effectively does&lt;br /&gt;
not exist. Designing a Capability Interface is exactly like designing any Java interface, so the particular details will&lt;br /&gt;
be glossed over in this section.&lt;br /&gt;
&lt;br /&gt;
The Capability Implementation, on the other hand, is the implementation of the previously defined Capability Interface.&lt;br /&gt;
Usual rules for interface implementations follow. There can be more than one Capability Implementation for each&lt;br /&gt;
capability. &lt;br /&gt;
&lt;br /&gt;
Note that a '''well-formed''' capability implementation should '''not store''' the Capability Provider inside of it: we&lt;br /&gt;
call the capability implementation ''provider-agnostic''. This is not a hard-requirement, though, rather it should act&lt;br /&gt;
more as a guideline. There are in fact certain situations where this cannot be avoided (e.g. attaching a client-synced&lt;br /&gt;
capability to an &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
Given all of the above information, this may be an example implementation of both a Capability Interface and a&lt;br /&gt;
Capability Implementation:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@AutoRegisterCapability&lt;br /&gt;
public interface MyCapability {&lt;br /&gt;
    String getValue();&lt;br /&gt;
    void setValue(String value);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
public class MyCapabilityImplementation implements MyCapability {&lt;br /&gt;
    private String value;&lt;br /&gt;
&lt;br /&gt;
    @Override&lt;br /&gt;
    public String getValue() {&lt;br /&gt;
        return this.value;&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    @Override&lt;br /&gt;
    public void setValue(String value) {&lt;br /&gt;
        this.value = value;&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that in this case, only a single implementation is provided.&lt;br /&gt;
&lt;br /&gt;
=== The Capability Provider ===&lt;br /&gt;
&lt;br /&gt;
The Capability Provider is an optional component of the capability that allows the Capability to be attached to a&lt;br /&gt;
component. The details on how a Capability Provider should behave have already been discussed in the two previous&lt;br /&gt;
sections [[#Exposing a Capability|Exposing a Capability]] and [[#Attaching a Capability|Attaching a Capability]]: refer&lt;br /&gt;
to those for more information.&lt;br /&gt;
&lt;br /&gt;
=== Tying it All Together ===&lt;br /&gt;
&lt;br /&gt;
Once all components of a Capability have been created, they must be registered so that the game is aware of the&lt;br /&gt;
capability's presence. The registration requires specifying only the Capability Interface.&lt;br /&gt;
&lt;br /&gt;
The registration can be performed by calling the &amp;lt;code&amp;gt;register&amp;lt;/code&amp;gt; method within the &amp;lt;code&amp;gt;RegisterCapabilitiesEvent&amp;lt;/code&amp;gt; which is fired on the &amp;lt;code&amp;gt;MOD&amp;lt;/code&amp;gt; event bus. The&lt;br /&gt;
registration will also automatically inject the created Capability into all relevant fields and methods: refer to&lt;br /&gt;
[[#Obtaining a Capability|Obtaining a Capability]] for more information.&lt;br /&gt;
&lt;br /&gt;
An example of registration can be found in the snippet that follows:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void registerCaps(RegisterCapabilitiesEvent event) {&lt;br /&gt;
    event.register(MyCapability.class);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Class Diagram ===&lt;br /&gt;
&lt;br /&gt;
[[File:Custom Capability Class Diagram.svg|800px|thumb|center|Custom Capability Class Diagram]]&lt;br /&gt;
&lt;br /&gt;
In the above diagram the green and red marked areas are classes from Minecraft and Forge respectively. The classes inside the purple area are only needed if you want to [[#Attaching a Capability|Attach a Capability]]. Furthermore this diagram models a persistent provider and its most basic form, for more information on how to create a more complex provider see [[#Custom Capability Providers|Custom Capability Providers]]. To create a volatile provider instead just do not implement &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Custom Capability Providers ==&lt;br /&gt;
&lt;br /&gt;
Much like custom Capabilities, Forge also allows the creation of custom Capability Providers. The main advantage of this&lt;br /&gt;
is allowing mods to create custom providers for their custom objects, in order to promote not only cross-mod&lt;br /&gt;
compatibility, but also uniformity in the way users may interact with different mod APIs.&lt;br /&gt;
&lt;br /&gt;
This section will only give the basic outline of what is necessary to implement a custom Capability Provider: for more&lt;br /&gt;
in-depth explanation, people are referred to the game code.&lt;br /&gt;
&lt;br /&gt;
By definition, a custom Capability Provider is everything that implements the &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt;&lt;br /&gt;
interface. In this section, though, we will only cover people that may want to replicate the functionality of one of&lt;br /&gt;
the default providers, such as &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; or &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
The easiest way of doing this is extending the &amp;lt;code&amp;gt;CapabilityProvider&amp;lt;/code&amp;gt; class provided by Forge. This will&lt;br /&gt;
automatically set up an ''agnostic'' Capability Provider. To fully initialize the capability provider, the subclass&lt;br /&gt;
should then invoke the &amp;lt;code&amp;gt;gatherCapabilities&amp;lt;/code&amp;gt; method as the last instruction in its constructor, to ensure that&lt;br /&gt;
the game is able to recollect and attach all capabilities that other mods may want to attach to the capability provider.&lt;br /&gt;
&lt;br /&gt;
== Code Examples ==&lt;br /&gt;
&lt;br /&gt;
* [https://gist.github.com/TheCurle/6db954d680f6f067dcdc791355c32c89 A Gist showing a quick and dirty example on how to implement a Capability effectively]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Category:Data Storage]]&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Capabilities&amp;diff=3330</id>
		<title>Capabilities</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Capabilities&amp;diff=3330"/>
		<updated>2022-09-24T18:05:16Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: Update Wiki to recent MinecraftForge PRs&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''Capabilities''' are a Forge system that allows cross-mod interactions by allowing capability ''providers'' to&lt;br /&gt;
dynamically respect contracts and provide specialized behavior without requiring the implementation of many interfaces&lt;br /&gt;
or hard dependencies on mods.&lt;br /&gt;
&lt;br /&gt;
== History ==&lt;br /&gt;
In an ideal world, all that would be needed for a mod to provide the equivalent of a capability would be implementing an&lt;br /&gt;
interface. This is in fact how cross-mod interaction used to work prior to the introduction of capabilities.&lt;br /&gt;
&lt;br /&gt;
The real world, though, is often much more complicated: users wanted to be free to combine mods the way they wanted and&lt;br /&gt;
saw fit, and developers wanted to be able to declare ''soft'' dependencies on other mods, thus reducing the need of&lt;br /&gt;
having a huge mod pack just for testing.&lt;br /&gt;
&lt;br /&gt;
The first approach used by Forge was conditional stripping of interfaces and methods, but this proved to be problematic.&lt;br /&gt;
While the idea works well in theory, in practice the ASM editing of classes relied on complex mechanics and could lead&lt;br /&gt;
to hard to spot bugs.&lt;br /&gt;
&lt;br /&gt;
For this reason, the entire system was redesigned and the concept of '''capabilities''' was born.&lt;br /&gt;
&lt;br /&gt;
== The Concept ==&lt;br /&gt;
A capability allows any capability provider to conditionally expose a certain ability to do something, e.g. accepting&lt;br /&gt;
power or handling items. A capability provider, moreover, can decide to expose a capability only on certain sides,&lt;br /&gt;
allowing for easy interactions with hoppers, cables, etc.&lt;br /&gt;
&lt;br /&gt;
Capabilities may also be added and removed dynamically both from the &amp;quot;owner&amp;quot; of the capability provider and other mods,&lt;br /&gt;
allowing even easier cross-mod interaction. For example, a mod that isn't compatible with Forge Energy could be&lt;br /&gt;
converted into one by dynamically attaching the Forge Energy capability and handling the conversion to a third-party&lt;br /&gt;
energy system without having to alter the original mod.&lt;br /&gt;
&lt;br /&gt;
== Terminology ==&lt;br /&gt;
The high flexibility of the system comes with a cost, though, which is terminology. The following section wants to be a&lt;br /&gt;
dictionary of sorts, defining all the terms that you may come across when dealing with capabilities.&lt;br /&gt;
&lt;br /&gt;
In the rest of this article, we will refer to these terms frequently, so make sure you are familiar with them.&lt;br /&gt;
&lt;br /&gt;
; Capability&lt;br /&gt;
: the ability to perform something. In-code this is represented by the &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; class.&lt;br /&gt;
; Capability Provider&lt;br /&gt;
: something that is able to support capabilities and provides a mean of accessing them. In-code they are represented by implementations of &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt;. There are multiple kinds of capability providers:&lt;br /&gt;
:; Volatile Provider&lt;br /&gt;
:: a provider that doesn't persist data to disk; once the provider ceases to exist for any number of reasons, all capability data gets deleted.&lt;br /&gt;
:; Persistent Provider&lt;br /&gt;
:: a provider that requires all capabilities to serialize data to disk, in order to persist data even across game restarts. They implement the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
:; Agnostic Provider&lt;br /&gt;
:: a provider that isn't neither volatile nor persistent, rather delegates the decision either to the capability directly or to sub-implementations. They also implement the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
; Capability Interface&lt;br /&gt;
: the interface that defines the contract of the capability, so what operations the capability exposes.&lt;br /&gt;
; Capability Implementation&lt;br /&gt;
: one of the possibly many implementations of the capability interface, that actually carries out the work.&lt;br /&gt;
&lt;br /&gt;
The wary reader may note that both ''persistent'' and ''agnostic'' providers are represented the same way in code. In&lt;br /&gt;
fact, the only difference between them comes from pure semantics in how their serialization methods are designed. This&lt;br /&gt;
will be further discussed in their respective sections.&lt;br /&gt;
&lt;br /&gt;
Moreover, it is also common to refer to the capability interface as simply the ''capability''. While not strictly&lt;br /&gt;
correct, due to common usage we will also use this convention. So, to refer to the capability interface&lt;br /&gt;
&amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt;, we will usually talk about the &amp;quot;&amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt; capability&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Forge-provided Capabilities and Providers ==&lt;br /&gt;
In order to ensure mods can work together seamlessly, Forge provides a set of default capabilities and capability&lt;br /&gt;
providers.&lt;br /&gt;
&lt;br /&gt;
The default capability providers in a Forge environment are: &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;Entity&amp;lt;/code&amp;gt;,&lt;br /&gt;
&amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;Level&amp;lt;/code&amp;gt;, and &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt;. These are all agnostic providers, since they don't&lt;br /&gt;
mandate any sort of capability persistency requirements. Rather, it is the job of whoever subclasses these providers to&lt;br /&gt;
deal with either volatile or non-volatile capabilities.&lt;br /&gt;
&lt;br /&gt;
The default capabilities that forge provides are represented by the interfaces &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt;,&lt;br /&gt;
&amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;IFluidHandlerItem&amp;lt;/code&amp;gt;, and &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt;. Each one of these capabilities will be discussed in the corresponding section.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IItemHandler&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to have some sort of internal&lt;br /&gt;
'''inventory''' with a certain number of slots, from which items can be inserted and extracted. It is also possible,&lt;br /&gt;
though, to expose this capability even if no such inventory is present as long as the capability provider can emulate&lt;br /&gt;
its presence (e.g. tools that allow accessing remote inventories).&lt;br /&gt;
&lt;br /&gt;
This effectively '''replaces''' the vanilla interfaces &amp;lt;code&amp;gt;Container&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;WorldlyContainer&amp;lt;/code&amp;gt;. These&lt;br /&gt;
interfaces are in fact retained only to allow vanilla code to compile and should not be used in mod code. This extends&lt;br /&gt;
to anything that implements those vanilla interfaces, such as &amp;lt;code&amp;gt;RandomizableContainerBlockEntity&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;ItemStackHandler&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IFluidHandler&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to handle and store fluids&lt;br /&gt;
in one or multiple fluid tanks. It is effectively the equivalent in terms of fluids of the &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt;&lt;br /&gt;
capability.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;TileFluidHandler&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IFluidHandlerItem&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IFluidHandlerItem&amp;lt;/code&amp;gt; capability refers to the ability for an &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt; capability provider&lt;br /&gt;
to handle and store fluids in one or multiple fluid tanks. It is basically a specialized version of the&lt;br /&gt;
&amp;lt;code&amp;gt;IFluidHandler&amp;lt;/code&amp;gt; capability that allows &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;s to define a custom container.&lt;br /&gt;
&lt;br /&gt;
=== &amp;lt;tt&amp;gt;IEnergyStorage&amp;lt;/tt&amp;gt; ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability refers to the ability for any capability provider to store, consume, and&lt;br /&gt;
produce energy. This capability is the base capability for what's commonly known in the modded world as Forge Energy (or&lt;br /&gt;
FE), i.e. the energy system most mods use. Its internal design is heavily based on the (now defunct) Redstone Flux&lt;br /&gt;
Energy API, supporting both a push and pull system.&lt;br /&gt;
&lt;br /&gt;
A default reference implementation for this capability interface is provided in &amp;lt;code&amp;gt;EnergyStorage&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Working with Capabilities ==&lt;br /&gt;
&lt;br /&gt;
Both capability providers and users need to be able to provide and access capabilities through a common framework,&lt;br /&gt;
otherwise the ideal of dynamic and mod-agnostic would not really exist. For this reason, both capability providers and&lt;br /&gt;
capability ''accessors'' (which we define as everything that wants to access a capability), also known as '''clients''' or '''users''',&lt;br /&gt;
need to work together and with Forge to ensure that the common interface is used sensibly and correctly by all parties.&lt;br /&gt;
&lt;br /&gt;
=== Obtaining a Capability ===&lt;br /&gt;
&lt;br /&gt;
Before being able to work with a capability, it is necessary to obtain an instance of the &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; object itself.&lt;br /&gt;
&lt;br /&gt;
A &amp;lt;code&amp;gt;Capability&amp;lt;/code&amp;gt; can obtained at any time using &amp;lt;code&amp;gt;CapabilityManager#get&amp;lt;/code&amp;gt;. This takes in an anonymous &amp;lt;code&amp;gt;CapabilityToken&amp;lt;/code&amp;gt; to still allow for a soft dependency system while also keeping hold of any generic information needed. As such, you can always obtain a non-null capability.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
public static Capability&amp;lt;IItemHandler&amp;gt; ITEM_HANDLER = CapabilityManager.get(new CapabilityToken&amp;lt;&amp;gt;(){});&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The above code will let Forge know that the field &amp;lt;code&amp;gt;ITEM_HANDLER&amp;lt;/code&amp;gt; should be analogous with the &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability. Note that this does not mean the capability is accessible or registered. To check if it is, call &amp;lt;code&amp;gt;Capability#isRegistered&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
This is, for obvious reasons, redundant, since all capabilities are available through&lt;br /&gt;
&amp;lt;code&amp;gt;ForgeCapabilities&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== Exposing a Capability ===&lt;br /&gt;
&lt;br /&gt;
Exposing a capability is a voluntary act by a capability provider that allows the capability to be discovered and&lt;br /&gt;
accessed by users.&lt;br /&gt;
&lt;br /&gt;
To do so, a capability provider needs to juggle a couple more moving pieces to ensure that the capability state remains&lt;br /&gt;
consistent and that the lookup remains fast. It is in fact possible for a capability provider to be asked to provide&lt;br /&gt;
many capabilities many times in the same tick. For this reason, a provider is asked to do the following:&lt;br /&gt;
&lt;br /&gt;
* the &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt;s that get returned '''must be cached''';&lt;br /&gt;
* if a capability changes exposure state (more on this later), all listeners '''must be notified''';&lt;br /&gt;
* if a capability gets invalidated (more on this later), all listeners '''must be notified'''&lt;br /&gt;
* the lookup inside &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; must be performed with '''an &amp;lt;code&amp;gt;if&amp;lt;/code&amp;gt;-&amp;lt;code&amp;gt;else&amp;lt;/code&amp;gt; chain''';&lt;br /&gt;
* all unexposed but still present capabilities '''should be available''' if the provider is queried with a &amp;lt;code&amp;gt;null&amp;lt;/code&amp;gt; direction (see ''Accessing a Capability'' for more information);&lt;br /&gt;
* if no capability of a given type is available or accessible, the provider '''must call &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt; as long as it is possible to do so'''.&lt;br /&gt;
&lt;br /&gt;
Capability providers must also reflect changes in the ''exposure state'' of a capability, meaning that if the&lt;br /&gt;
accessibility of a capability from a certain &amp;lt;code&amp;gt;Direction&amp;lt;/code&amp;gt; changes (refer to&lt;br /&gt;
[[#Accessing a Capability|Accessing a Capability]] for more information), it is the provider's responsibility to trigger&lt;br /&gt;
a state response by invalidating the returned &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; and caching a new one. This should also be&lt;br /&gt;
performed when a capability gets ''invalidated'', such as when a capability provider gets removed.&lt;br /&gt;
&lt;br /&gt;
With all of the above in mind, part of a capability provider implementation may be similar to the following snippet:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
// suppose the presence of a field 'inventory' of type 'IItemHandler'&lt;br /&gt;
&lt;br /&gt;
private LazyOptional&amp;lt;IItemhandler&amp;gt; inventoryOptional = LazyOptional.empty();&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; capability, @Nullable Direction direction) {&lt;br /&gt;
    if (capability == ForgeCapabilities.ITEM_HANDLER&lt;br /&gt;
            &amp;amp;&amp;amp; (direction == null || direction == Direction.UP || direction == Direction.DOWN)) {&lt;br /&gt;
        return this.inventoryOptional.cast();&lt;br /&gt;
    }&lt;br /&gt;
    return super.getCapability(capability, direction); // See note after snippet&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
public void invalidateCaps()&lt;br /&gt;
{&lt;br /&gt;
    this.inventoryOptional = LazyOptional.of(() -&amp;gt; this.inventory);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
protected void invalidateCaps() {&lt;br /&gt;
    super.invalidateCaps();&lt;br /&gt;
    this.inventoryOptional.invalidate();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This possible implementation of a capability provider exposes an &amp;lt;code&amp;gt;IItemHandler&amp;lt;/code&amp;gt; capability and restricts&lt;br /&gt;
access only to the &amp;lt;code&amp;gt;UP&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;DOWN&amp;lt;/code&amp;gt; directions. If we assume this capability provider is a&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, then we may also say that the inventory is only accessible from the top and the bottom of the&lt;br /&gt;
block.&lt;br /&gt;
&lt;br /&gt;
Moreover, the capability gets automatically invalidated when the provider gets invalidated. Assuming this is a&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, this usually happens when the block gets removed from the level or unloaded due to distance.&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt; call at the end of the &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; method is extremely important, since it's what&lt;br /&gt;
allows Attaching external Capabilities to capability providers. Nevertheless, it is not always possible to invoke&lt;br /&gt;
&amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt;: in those cases, an empty &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; should be returned.&lt;br /&gt;
&lt;br /&gt;
=== Attaching a Capability ===&lt;br /&gt;
&lt;br /&gt;
Attaching a Capability is a process by which external agents &amp;quot;modify&amp;quot; a Capability Provider, making it expose additional&lt;br /&gt;
capabilities other than the already available ones.&lt;br /&gt;
&lt;br /&gt;
To do so, the '''attaching agent''' (which means the thing that wants to attach a capability to another provider) must&lt;br /&gt;
listen to the &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;T&amp;amp;gt;&amp;lt;/code&amp;gt;. The &amp;lt;code&amp;gt;T&amp;lt;/code&amp;gt; in this case represents the capability&lt;br /&gt;
provider you want to attach the capability to. Note that the type of &amp;lt;code&amp;gt;T&amp;lt;/code&amp;gt; '''must''' be the base type of the&lt;br /&gt;
capability provider, not a subclass. As an example, if you want to attach a capability to a &amp;lt;code&amp;gt;MyBlockEntity&amp;lt;/code&amp;gt;,&lt;br /&gt;
which extends &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, you'll have to listen to &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;BlockEntity&amp;amp;gt;&amp;lt;/code&amp;gt;,&lt;br /&gt;
'''NOT''' to &amp;lt;code&amp;gt;AttachCapabilitiesEvent&amp;amp;lt;MyBlockEntity&amp;amp;gt;&amp;lt;/code&amp;gt;, since the latter will never fire.&lt;br /&gt;
&lt;br /&gt;
The attaching agent can use the provided methods &amp;lt;code&amp;gt;getObject&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;addCapability&amp;lt;/code&amp;gt;, and &lt;br /&gt;
&amp;lt;code&amp;gt;addListener&amp;lt;/code&amp;gt; to check whether the capability should be attached to the current object and perform the&lt;br /&gt;
desired action.&lt;br /&gt;
&lt;br /&gt;
When attaching a capability, the attaching agent should also provide a name in the form of a&lt;br /&gt;
&amp;lt;code&amp;gt;ResourceLocation&amp;lt;/code&amp;gt;. The name '''must''' be under the attaching agent's namespace, but no restrictions are&lt;br /&gt;
placed on the actual name, as long as it is unique inside the given namespace.&lt;br /&gt;
&lt;br /&gt;
Maybe a little counter-intuitively, the process of attaching does not attach a capability nor a capability interface&lt;br /&gt;
directly. Rather, the attaching agent should create its own implementation of a '''Capability Provider''' and attach it&lt;br /&gt;
via the event. This is done so that the attaching agent can have control over when, how, and where its capabilities are&lt;br /&gt;
exposed, instead of relying on the game itself deciding these parameters. For this reason, all considerations given in&lt;br /&gt;
the [[#Exposing a Capability|Exposing a Capability]] section on how to correctly create a Capability Provider.&lt;br /&gt;
&lt;br /&gt;
With the above in mind, part of an attaching agent may be similar to the following snippet of code:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void onAttachingCapabilities(final AttachCapabilitiesEvent&amp;lt;BlockEntity&amp;gt; event) {&lt;br /&gt;
    if (!(event.getObject() instanceof EnergyBasedBlockEntity)) return;&lt;br /&gt;
&lt;br /&gt;
    EnergyStorage backend = new EnergyStorage(((EnergyBasedBlockEntity) event.getObject()).capacity);&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; optionalStorage = LazyOptional.of(() -&amp;gt; backend);&lt;br /&gt;
&lt;br /&gt;
    ICapabilityProvider provider = new ICapabilityProvider() {&lt;br /&gt;
        @Override&lt;br /&gt;
        public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; cap, @Nullable Direction direction) {&lt;br /&gt;
            if (cap == ForgeCapabilities.ENERGY) {&lt;br /&gt;
                return optionalStorage.cast();&lt;br /&gt;
            }&lt;br /&gt;
            return LazyOptional.empty();&lt;br /&gt;
        }&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    event.addCapability(new ResourceLocation(&amp;quot;examplemod&amp;quot;, &amp;quot;fe_compatibility&amp;quot;), provider);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This example implementation of an attaching agent attaches a &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability to all&lt;br /&gt;
&amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; instance that are a subclass of &amp;lt;code&amp;gt;EnergyBasedBlockEntity&amp;lt;/code&amp;gt;. It also sets up the&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; for invalidation if the parent capability provider gets invalidated.&lt;br /&gt;
&lt;br /&gt;
Note also the call of &amp;lt;code&amp;gt;LazyOptional.empty()&amp;lt;/code&amp;gt; rather than a &amp;lt;code&amp;gt;super&amp;lt;/code&amp;gt;. This is needed because when&lt;br /&gt;
attaching a capability, the parent capability provider isn't known. For this reason, it is necessary to return an empty&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt;. The game will then handle automatic merging of the various different providers into a single&lt;br /&gt;
one.&lt;br /&gt;
&lt;br /&gt;
The above example is one of a '''Volatile''' Capability Provider. On the other hand, mods may want to persist their&lt;br /&gt;
data across sessions. In this case, they should attach a '''Persistent''' Capability Provider: this can be done either&lt;br /&gt;
by implementing the &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt; interface along with &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt; or by&lt;br /&gt;
implementing the &amp;lt;code&amp;gt;ICapabilitySerializable&amp;lt;/code&amp;gt; interface.&lt;br /&gt;
&lt;br /&gt;
The previous example reworked to use a Persistent Capability Provider may be similar to the following snippet:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void onAttachingCapabilities(final AttachCapabilitiesEvent&amp;lt;BlockEntity&amp;gt; event) {&lt;br /&gt;
    if (!(event.getObject() instanceof EnergyBasedBlockEntity)) return;&lt;br /&gt;
&lt;br /&gt;
    EnergyStorage backend = new EnergyStorage(((EnergyBasedBlockEntity) event.getObject()).capacity);&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; optionalStorage = LazyOptional.of(() -&amp;gt; backend);&lt;br /&gt;
    Capability&amp;lt;IEnergyStorage&amp;gt; capability = ForgeCapabilities.ENERGY;&lt;br /&gt;
&lt;br /&gt;
    ICapabilityProvider provider = new ICapabilitySerializable&amp;lt;IntTag&amp;gt;() {&lt;br /&gt;
        @Override&lt;br /&gt;
        public &amp;lt;T&amp;gt; LazyOptional&amp;lt;T&amp;gt; getCapability(Capability&amp;lt;T&amp;gt; cap, @Nullable Direction direction) {&lt;br /&gt;
            if (cap == capability) {&lt;br /&gt;
                return optionalStorage.cast();&lt;br /&gt;
            }&lt;br /&gt;
            return LazyOptional.empty();&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @Override&lt;br /&gt;
        public IntTag serializeNBT() {&lt;br /&gt;
            return backend.serializeNBT();&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @Override&lt;br /&gt;
        public void deserializeNBT(IntTag tag) {&lt;br /&gt;
            backend.deserializeNBT(tag);&lt;br /&gt;
        }&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    event.addCapabilities(new ResourceLocation(&amp;quot;examplemod&amp;quot;, &amp;quot;fe_compatibility&amp;quot;), provider);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that when using capabilities on entities, you should manually invalidate the capability via &amp;lt;code&amp;gt;invalidateCaps()&amp;lt;/code&amp;gt;, via etc. &amp;lt;code&amp;gt;PlayerEvent.Clone&amp;lt;/code&amp;gt;. This is due to the fact that players are recreated &amp;amp; copied when moving across dimensions, not simply moved.&lt;br /&gt;
&lt;br /&gt;
=== Accessing a Capability ===&lt;br /&gt;
&lt;br /&gt;
Accessing a Capability is the process by which a user is able to '''query''' a Capability Provider for a specific&lt;br /&gt;
instance of a capability.&lt;br /&gt;
&lt;br /&gt;
This is perhaps the second most important part of the entire capability system, since it is what allows cross-mod&lt;br /&gt;
interaction. To obtain an instance of a Capability, the user must first get a hold of the Capability Provider that&lt;br /&gt;
should be queried. This can be done in a variety of ways and is outside the scope of this article. The user should&lt;br /&gt;
then invoke the &amp;lt;code&amp;gt;getCapability&amp;lt;/code&amp;gt; method passing the unique instance of the capability that should be queried&lt;br /&gt;
(see [[#Obtaining a Capability|Obtaining a Capability]] for more information) and the querying &amp;lt;code&amp;gt;Direction&amp;lt;/code&amp;gt;,&lt;br /&gt;
if applicable.&lt;br /&gt;
&lt;br /&gt;
The returned object is a &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; wrapping the queried Capability, if the capability provider exposes&lt;br /&gt;
it, otherwise it will be empty. The &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; can be either unwrapped via an &amp;lt;code&amp;gt;orElse&amp;lt;/code&amp;gt; or&lt;br /&gt;
used directly via &amp;lt;code&amp;gt;ifPresent&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
It is '''highly suggested''' to cache the returned &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; to avoid querying the same provider every&lt;br /&gt;
time, in order to improve performance. The user should thus register itself to the invalidation listener via the&lt;br /&gt;
&amp;lt;code&amp;gt;addListener&amp;lt;/code&amp;gt; method. This ensures that the user will be able to react to the invalidation of the&lt;br /&gt;
&amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; and remove it from the cache.&lt;br /&gt;
&lt;br /&gt;
With the above in mind, part of an user may be similar to the following snippet of code:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
// note the use of EnumMap, which is much more performant than HashMap for enum keys&lt;br /&gt;
private final Map&amp;lt;Direction, LazyOptional&amp;lt;IEnergyStorage&amp;gt;&amp;gt; cache = new EnumMap&amp;lt;&amp;gt;(Direction.class);&lt;br /&gt;
&lt;br /&gt;
private void sendPowerTo(int power, Direction direction) {&lt;br /&gt;
    LazyOptional&amp;lt;IEnergyStorage&amp;gt; targetCapability = cache.get(direction);&lt;br /&gt;
&lt;br /&gt;
    if (targetCapability == null) {&lt;br /&gt;
        ICapabilityProvider provider = level.getBlockEntity(pos.relative(direction));&lt;br /&gt;
        targetCapability = provider.getCapability(ForgeCapabilities.ENERGY, direction.getOpposite());&lt;br /&gt;
        cache.put(direction, targetCapability);&lt;br /&gt;
        targetCapability.addListener(self -&amp;gt; cache.put(direction, null));&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    targetCapability.ifPresent(storage -&amp;gt; storage.receiveEnergy(power, false));&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This example implementation of an user is querying via a &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; the neighboring capability provider&lt;br /&gt;
for an &amp;lt;code&amp;gt;IEnergyStorage&amp;lt;/code&amp;gt; capability. Before obtaining the provider, the code performs a cache lookup for the&lt;br /&gt;
targeted capability. If the check succeeds, then no lookup is performed; if the check fails, the targeted Capability&lt;br /&gt;
Provider is obtained and queried for the Capability. The obtained &amp;lt;code&amp;gt;LazyOptional&amp;lt;/code&amp;gt; is then cached and a&lt;br /&gt;
listener is attached to it so that the cache would be emptied on invalidation. The code then continues with the&lt;br /&gt;
interaction with the capability, which is outside the scope of this article.&lt;br /&gt;
&lt;br /&gt;
== Creating Custom Capabilities ==&lt;br /&gt;
&lt;br /&gt;
While the various capabilities provided by Forge may satisfy the most common use cases, there is always the chance that&lt;br /&gt;
a mod may require a custom solution. For this reason, Forge provides a way to define a custom Capability.&lt;br /&gt;
&lt;br /&gt;
Defining a custom Capability requires the user to provide one main component: the Capability Interface. Optionally, a &lt;br /&gt;
Capability Implementation and Capability Provider can also be created. In this&lt;br /&gt;
case, the provider will be used as described in [[#Attaching a Capability|Attaching a Capability]]. The various details &lt;br /&gt;
for all these components are described in the respective sections of this article.&lt;br /&gt;
&lt;br /&gt;
In this section, we will refer to the implementation of a &amp;lt;code&amp;gt;MyCapability&amp;lt;/code&amp;gt; capability, that can be used to&lt;br /&gt;
store a single mutable &amp;lt;code&amp;gt;String&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Refer also to [[#Code Examples|Code Examples]] for an example on how the various components may be implemented in a&lt;br /&gt;
real-world scenario.&lt;br /&gt;
&lt;br /&gt;
=== The Capability Interface and the Capability Implementation ===&lt;br /&gt;
&lt;br /&gt;
The Capability Interface is one of the most important parts of a Capability: without it, the Capability effectively does&lt;br /&gt;
not exist. Designing a Capability Interface is exactly like designing any Java interface, so the particular details will&lt;br /&gt;
be glossed over in this section.&lt;br /&gt;
&lt;br /&gt;
The Capability Implementation, on the other hand, is the implementation of the previously defined Capability Interface.&lt;br /&gt;
Usual rules for interface implementations follow. There can be more than one Capability Implementation for each&lt;br /&gt;
capability. &lt;br /&gt;
&lt;br /&gt;
Note that a '''well-formed''' capability implementation should '''not store''' the Capability Provider inside of it: we&lt;br /&gt;
call the capability implementation ''provider-agnostic''. This is not a hard-requirement, though, rather it should act&lt;br /&gt;
more as a guideline. There are in fact certain situations where this cannot be avoided (e.g. attaching a client-synced&lt;br /&gt;
capability to an &amp;lt;code&amp;gt;ItemStack&amp;lt;/code&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
Given all of the above information, this may be an example implementation of both a Capability Interface and a&lt;br /&gt;
Capability Implementation:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
public interface MyCapability {&lt;br /&gt;
    String getValue();&lt;br /&gt;
    void setValue(String value);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
public class MyCapabilityImplementation implements MyCapability {&lt;br /&gt;
    private String value;&lt;br /&gt;
&lt;br /&gt;
    @Override&lt;br /&gt;
    public String getValue() {&lt;br /&gt;
        return this.value;&lt;br /&gt;
    }&lt;br /&gt;
&lt;br /&gt;
    @Override&lt;br /&gt;
    public void setValue(String value) {&lt;br /&gt;
        this.value = value;&lt;br /&gt;
    }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that in this case, only a single implementation is provided.&lt;br /&gt;
&lt;br /&gt;
=== The Capability Provider ===&lt;br /&gt;
&lt;br /&gt;
The Capability Provider is an optional component of the capability that allows the Capability to be attached to a&lt;br /&gt;
component. The details on how a Capability Provider should behave have already been discussed in the two previous&lt;br /&gt;
sections [[#Exposing a Capability|Exposing a Capability]] and [[#Attaching a Capability|Attaching a Capability]]: refer&lt;br /&gt;
to those for more information.&lt;br /&gt;
&lt;br /&gt;
=== Tying it All Together ===&lt;br /&gt;
&lt;br /&gt;
Once all components of a Capability have been created, they must be registered so that the game is aware of the&lt;br /&gt;
capability's presence. The registration requires specifying only the Capability Interface.&lt;br /&gt;
&lt;br /&gt;
The registration can be performed by calling the &amp;lt;code&amp;gt;register&amp;lt;/code&amp;gt; method within the &amp;lt;code&amp;gt;RegisterCapabilitiesEvent&amp;lt;/code&amp;gt; which is fired on the &amp;lt;code&amp;gt;MOD&amp;lt;/code&amp;gt; event bus. The&lt;br /&gt;
registration will also automatically inject the created Capability into all relevant fields and methods: refer to&lt;br /&gt;
[[#Obtaining a Capability|Obtaining a Capability]] for more information.&lt;br /&gt;
&lt;br /&gt;
An example of registration can be found in the snippet that follows:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@SubscribeEvent&lt;br /&gt;
public void registerCaps(RegisterCapabilitiesEvent event) {&lt;br /&gt;
    event.register(MyCapability.class);&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Class Diagram ===&lt;br /&gt;
&lt;br /&gt;
[[File:Custom Capability Class Diagram.svg|800px|thumb|center|Custom Capability Class Diagram]]&lt;br /&gt;
&lt;br /&gt;
In the above diagram the green and red marked areas are classes from Minecraft and Forge respectively. The classes inside the purple area are only needed if you want to [[#Attaching a Capability|Attach a Capability]]. Furthermore this diagram models a persistent provider and its most basic form, for more information on how to create a more complex provider see [[#Custom Capability Providers|Custom Capability Providers]]. To create a volatile provider instead just do not implement &amp;lt;code&amp;gt;INBTSerializable&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Custom Capability Providers ==&lt;br /&gt;
&lt;br /&gt;
Much like custom Capabilities, Forge also allows the creation of custom Capability Providers. The main advantage of this&lt;br /&gt;
is allowing mods to create custom providers for their custom objects, in order to promote not only cross-mod&lt;br /&gt;
compatibility, but also uniformity in the way users may interact with different mod APIs.&lt;br /&gt;
&lt;br /&gt;
This section will only give the basic outline of what is necessary to implement a custom Capability Provider: for more&lt;br /&gt;
in-depth explanation, people are referred to the game code.&lt;br /&gt;
&lt;br /&gt;
By definition, a custom Capability Provider is everything that implements the &amp;lt;code&amp;gt;ICapabilityProvider&amp;lt;/code&amp;gt;&lt;br /&gt;
interface. In this section, though, we will only cover people that may want to replicate the functionality of one of&lt;br /&gt;
the default providers, such as &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; or &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
The easiest way of doing this is extending the &amp;lt;code&amp;gt;CapabilityProvider&amp;lt;/code&amp;gt; class provided by Forge. This will&lt;br /&gt;
automatically set up an ''agnostic'' Capability Provider. To fully initialize the capability provider, the subclass&lt;br /&gt;
should then invoke the &amp;lt;code&amp;gt;gatherCapabilities&amp;lt;/code&amp;gt; method as the last instruction in its constructor, to ensure that&lt;br /&gt;
the game is able to recollect and attach all capabilities that other mods may want to attach to the capability provider.&lt;br /&gt;
&lt;br /&gt;
== Code Examples ==&lt;br /&gt;
&lt;br /&gt;
* [https://gist.github.com/TheCurle/6db954d680f6f067dcdc791355c32c89 A Gist showing a quick and dirty example on how to implement a Capability effectively]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Category:Data Storage]]&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Block_Entities&amp;diff=3328</id>
		<title>Block Entities</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Block_Entities&amp;diff=3328"/>
		<updated>2022-09-20T18:01:23Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Block entities are like simplified entities that are bound to a &amp;lt;code&amp;gt;Block&amp;lt;/code&amp;gt;. They are used to store dynamic data, execute tick based tasks and for dynamic rendering. Some examples from vanilla Minecraft would be: handling of inventories (chests), smelting logic on furnaces, or area effects for beacons. More advanced examples exist in mods, such as quarries, sorting machines, pipes, and displays.&lt;br /&gt;
&lt;br /&gt;
{{Colored box|title=Tip|content=A &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; isn’t a solution for everything, and they can cause lag when used wrongly. When possible, try to avoid them.}}&lt;br /&gt;
&lt;br /&gt;
== Creating a &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; ==&lt;br /&gt;
You can also use a &amp;lt;code&amp;gt;DeferredRegister&amp;lt;/code&amp;gt; instead.&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
public static final DeferredRegister&amp;lt;BlockEntityType&amp;lt;?&amp;gt;&amp;gt; BLOCK_ENTITIES = DeferredRegister.create(ForgeRegistries.BLOCK_ENTITIES, &amp;quot;examplemod&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
public static final RegistryObject&amp;lt;BlockEntityType&amp;lt;?&amp;gt;&amp;gt; MY_BE = BLOCK_ENTITIES.register(&amp;quot;mybe&amp;quot;, () -&amp;gt; BlockEntityType.Builder.of(supplier, validBlocks).build(null));&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In this example, &amp;lt;code&amp;gt;supplier&amp;lt;/code&amp;gt; is a &amp;lt;code&amp;gt;BlockEntityType$BlockEntitySupplier&amp;lt;/code&amp;gt; that creates a new instance of your &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;. A method reference or a lambda is commonly used. The variable &amp;lt;code&amp;gt;validBlocks&amp;lt;/code&amp;gt; is one or more blocks (&amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;BlockEntityType$Builder::of&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; is varargs) that the block entity can exist for.&lt;br /&gt;
&lt;br /&gt;
== Attaching a &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; to a &amp;lt;code&amp;gt;Block&amp;lt;/code&amp;gt; ==&lt;br /&gt;
To attach your new &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; to a &amp;lt;code&amp;gt;Block&amp;lt;/code&amp;gt;, the &amp;lt;code&amp;gt;EntityBlock&amp;lt;/code&amp;gt; interface must be implemented on your &amp;lt;code&amp;gt;Block&amp;lt;/code&amp;gt; subclass. The method &amp;lt;code&amp;gt;EntityBlock#newBlockEntity(BlockPos, BlockState)&amp;lt;/code&amp;gt; must be implemented and return a new instance of your &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
== Storing Data within your &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; ==&lt;br /&gt;
In order to save data, override the following two methods &lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
BlockEntity#saveAdditional(CompoundTag tag)&lt;br /&gt;
&lt;br /&gt;
BlockEntity#load(CompoundTag tag)&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
These methods are called whenever the &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt; containing the &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; gets loaded from/saved to a tag. Use them to read and write to the fields in your block entity class.&lt;br /&gt;
&lt;br /&gt;
{{Colored box|title=Tip|content=Whenever your data changes you need to call &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;BlockEntity#setChanged()&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;, otherwise the &amp;lt;code&amp;gt;LevelChunk&amp;lt;/code&amp;gt; containing your &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; might be skipped while the level is saved.}}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
{{Tip/Important|It is important that you call the super methods!&lt;br /&gt;
&lt;br /&gt;
The tag names &amp;lt;code&amp;gt;id&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;x&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;y&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;z&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;ForgeData&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;ForgeCaps&amp;lt;/code&amp;gt; are reserved by the super methods.}}&lt;br /&gt;
&lt;br /&gt;
== Ticking &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; ==&lt;br /&gt;
If you need a ticking &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;, for example to keep track of the progress during a smelting process, another method must be implemented and overridden within &amp;lt;code&amp;gt;EntityBlock&amp;lt;/code&amp;gt;: &amp;lt;code&amp;gt;EntityBlock#getTicker(Level, BlockState, BlockEntityType)&amp;lt;/code&amp;gt;. This can implement different tickers depending on which logical side the user is on, or just implement one general ticker. In either case, a &amp;lt;code&amp;gt;BlockEntityTicker&amp;lt;/code&amp;gt; must be returned. Since this is a functional interface, it can just take in a method representing the ticker instead:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
// Inside some Block subclass&lt;br /&gt;
@Nullable&lt;br /&gt;
@Override&lt;br /&gt;
public &amp;lt;T extends BlockEntity&amp;gt; BlockEntityTicker&amp;lt;T&amp;gt; getTicker(Level level, BlockState state, BlockEntityType&amp;lt;T&amp;gt; type) {&lt;br /&gt;
  return type == MyBlockEntityTypes.MY_BE.get() ? MyBlockEntity::tick : null;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
// Inside MyBlockEntity&lt;br /&gt;
public static void tick(Level level, BlockPos pos, BlockState state, T blockEntity) {&lt;br /&gt;
  // Do stuff&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{Colored box|title=Tip|content=This method is called each tick. Therefore, you should avoid having complicated calculations in here. If possible, you should make more complex calculations just every X ticks. (The amount of ticks in a second may be lower than 20 (twenty) but won’t be higher)}}&lt;br /&gt;
&lt;br /&gt;
== Synchronizing the Data to the Client ==&lt;br /&gt;
There are 3 (three) ways of syncing data to the client. Synchronizing on chunk load, synchronizing on block updates and synchronizing with a custom network message.&lt;br /&gt;
=== Synchronizing on LevelChunk load  ===&lt;br /&gt;
For this you need to override &lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
BlockEntity#getUpdateTag()&lt;br /&gt;
&lt;br /&gt;
IForgeBlockEntity#handleUpdateTag(CompoundTag tag)&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
Again, this is pretty simple, the first method collects the data that should be send to the client, while the second one processes that data. If your &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; doesn’t contain much data you might be able to use the methods out of the [[#storing_data|Storing Data]] section.&lt;br /&gt;
&lt;br /&gt;
{{Tip/Important|Synchronizing excessive/useless data for block entities can lead to network congestion. You should optimize your network usage by sending only the information the client needs when the client needs it. For instance, it is more often than not unnecessary to send the inventory of a block entity in the update tag, as this can be synchronized via its &amp;lt;code&amp;gt;AbstractContainerMenu&amp;lt;/code&amp;gt;.)}}&lt;br /&gt;
&lt;br /&gt;
=== Synchronizing on block update  ===&lt;br /&gt;
This method is a bit more complicated, but again you just need to override 2 or 3 methods. Here is a tiny example implementation of it:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
@Override&lt;br /&gt;
public CompoundTag getUpdateTag() {&lt;br /&gt;
  CompoundTag tag = new CompoundTag();&lt;br /&gt;
  //Write your data into the tag&lt;br /&gt;
  return tag;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@Override&lt;br /&gt;
public Packet&amp;lt;ClientGamePacketListener&amp;gt; getUpdatePacket() {&lt;br /&gt;
  // Will get tag from #getUpdateTag&lt;br /&gt;
  return ClientboundBlockEntityDataPacket.create(this);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
// Can override IForgeBlockEntity#onDataPacket. By default, this will defer to the #load.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
The static constructors &amp;lt;code&amp;gt;ClientboundBlockEntityDataPacket#create&amp;lt;/code&amp;gt; takes:&lt;br /&gt;
* The &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;.&lt;br /&gt;
* An optional function to get the &amp;lt;code&amp;gt;CompoundTag&amp;lt;/code&amp;gt; from the &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;. By default, this uses &amp;lt;code&amp;gt;BlockEntity#getUpdateTag&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Now, to send the packet, an update notification must be given on the server. &lt;br /&gt;
&amp;lt;code&amp;gt;&lt;br /&gt;
Level#sendBlockUpdated(BlockPos pos, BlockState oldState, BlockState newState, int flags)&lt;br /&gt;
&amp;lt;/code&amp;gt;&lt;br /&gt;
The &amp;lt;code&amp;gt;pos&amp;lt;/code&amp;gt; should be your &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt;’s position. For &amp;lt;code&amp;gt;oldState&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;newState&amp;lt;/code&amp;gt; you can pass the current &amp;lt;code&amp;gt;BlockState&amp;lt;/code&amp;gt; at that position. The &amp;lt;code&amp;gt;flags&amp;lt;/code&amp;gt; are a bitmask and should contain &amp;lt;code&amp;gt;2&amp;lt;/code&amp;gt;, which will sync the changes to the client. See &amp;lt;code&amp;gt;Block&amp;lt;/code&amp;gt; for more info as well as the rest of the flags. The flag &amp;lt;code&amp;gt;2&amp;lt;/code&amp;gt; is equivalent to &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;Block#UPDATE_CLIENTS&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== Synchronizing using a custom network message ===&lt;br /&gt;
&lt;br /&gt;
This way of synchronizing is probably the most complicated one, but is usually also the most optimized one, as you can make sure that only the data you need to be synchronized is actually synchronized. You should first check out the &amp;lt;code&amp;gt;[[Understanding Networking|Networking]]&amp;lt;/code&amp;gt; section and especially &amp;lt;code&amp;gt;[[Using SimpleChannel|SimpleImpl]]&amp;lt;/code&amp;gt; before attempting this. Once you’ve created your custom network message, you can send it to all users that have the &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; loaded with: &lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
SimpleChannel#send(PacketDistributor.TRACKING_CHUNK.with(() -&amp;gt; chunk), MSG);&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
{{Colored box|title=Alert|content=It is important that you do safety checks, the &amp;lt;code&amp;gt;BlockEntity&amp;lt;/code&amp;gt; might already be destroyed/replaced when the message arrives at the player! You should also check if the area is loaded using (&amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;Level#hasChunkAt(BlockPos)&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;)}}&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Datageneration/Loot_Tables&amp;diff=3327</id>
		<title>Datageneration/Loot Tables</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Datageneration/Loot_Tables&amp;diff=3327"/>
		<updated>2022-09-20T17:57:56Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==The LootTableProvider class==&lt;br /&gt;
First you would need a new class that extends &amp;lt;code&amp;gt;LootTableProvider&amp;lt;/code&amp;gt;. In this class you will override the &amp;lt;code&amp;gt;getTables&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;validate&amp;lt;/code&amp;gt; methods.&lt;br /&gt;
You can optionally override &amp;lt;code&amp;gt;getName&amp;lt;/code&amp;gt; to return a name for the logs, if you have multiple providers and don't want to simply show up as &amp;quot;LootTables&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
None of the methods you will be overriding (either here or, where applicable, on the subproviders) should call the superclass methods - these superclass methods implement the vanilla data generation.&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;getTables&amp;lt;/code&amp;gt; method will return a list of subproviders (explained further in the next section), the function signature looks a bit overwhelming but the actual method body is simple. Each subprovider will typically be a class, and you can simply use their constructors here. For more advanced scenarios (e.g. if you want to organize subproviders for multiple parameter sets into a single class), you can use a lambda that returns another lambda or a method reference.&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
    @Override&lt;br /&gt;
    protected List&amp;lt;Pair&amp;lt;Supplier&amp;lt;Consumer&amp;lt;BiConsumer&amp;lt;ResourceLocation, LootTable.Builder&amp;gt;&amp;gt;&amp;gt;, LootContextParamSet&amp;gt;&amp;gt; getTables() {&lt;br /&gt;
        return List.of(&lt;br /&gt;
            Pair.of(MyBlockLoot::new, LootContextParamSets.BLOCK),&lt;br /&gt;
            Pair.of(MyEntityLoot::new, LootContextParamSets.ENTITY),&lt;br /&gt;
            Pair.of(MyChestLoot::new, LootContextParamSets.CHEST));&lt;br /&gt;
    }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;validate&amp;lt;/code&amp;gt; method needs to be overriden to eliminate the part of the vanilla code that verifies that the vanilla special loot tables have all been defined. If you have special loot tables (i.e. any loot table other than the main loot table for a block or entity), you may wish to add similar verification code here. The remaining code ensures that each table is consistent with the associated parameter set (e.g. that you're not trying to access a block state in an entity loot table).&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
    @Override&lt;br /&gt;
    protected void validate(Map&amp;lt;ResourceLocation, LootTable&amp;gt; map, ValidationContext validationtracker) {&lt;br /&gt;
        map.forEach((location, lootTable) -&amp;gt; LootTables.validate(validationtracker, location, lootTable);&lt;br /&gt;
    }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Subproviders==&lt;br /&gt;
Each subprovider is a &amp;lt;code&amp;gt;Consumer&amp;lt;BiConsumer&amp;lt;ResourceLocation, LootTable.Builder&amp;gt;&amp;gt;&amp;lt;/code&amp;gt;. This is a fancy name that means that it has an accept function that is called with an argument containing another function that it can call with each loot table it wants to create.&lt;br /&gt;
&lt;br /&gt;
Each vanilla subprovider is a class. BlockLoot and EntityLoot contain helper methods to ensure that every block or entity has a primary loot table and to help generate certain types of loot tables. BlockLoot in particular has a large collection of helper functions that are extremely useful for implementing standard forms of loot tables for block types such as ores, doors, slabs, crops, or any block that simply always drops itself as an item.&lt;br /&gt;
&lt;br /&gt;
===Extending BlockLoot or EntityLoot===&lt;br /&gt;
If you are extending BlockLoot or EntityLoot, you will need to override the &amp;lt;code&amp;gt;addTables&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;getKnownBlocks&amp;lt;/code&amp;gt; or &amp;lt;code&amp;gt;getKnownEntities&amp;lt;/code&amp;gt; methods. From the &amp;lt;code&amp;gt;addTables&amp;lt;/code&amp;gt; methods you will call the &amp;lt;code&amp;gt;add&amp;lt;/code&amp;gt; method for each of the tables you wish to create (a handful of the helper functions in BlockLoot including &amp;lt;code&amp;gt;dropSelf&amp;lt;/code&amp;gt; automatically add the tables they create).&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
    @Override&lt;br /&gt;
    protected void addTables() {&lt;br /&gt;
        dropSelf(ModBlocks.BLOCK1.get());&lt;br /&gt;
        add(ModBlocks.BLOCK2.get(), ...);&lt;br /&gt;
    }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The second parameter to &amp;lt;code&amp;gt;BlockLoot.add&amp;lt;/code&amp;gt; may be a function that accepts the Block and returns a LootTable.Builder, or the LootTable.Builder itself. Many of the helper functions in BlockLoot work this way. For &amp;lt;code&amp;gt;EntityLoot.add&amp;lt;/code&amp;gt;, it must simply be the LootTable.Builder, but the first argument may be a ResourceLocation to create a special loot table rather than the primary loot table for the entity (this is used by vanilla for sheep colors).&lt;br /&gt;
&lt;br /&gt;
You must override &amp;lt;code&amp;gt;getKnownBlocks&amp;lt;/code&amp;gt; or &amp;lt;code&amp;gt;getKnownEntities&amp;lt;/code&amp;gt;, respectively, to return only the blocks or entity types registered by your mod.&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
    @Override&lt;br /&gt;
    protected Iterable&amp;lt;Block&amp;gt; getKnownBlocks() {&lt;br /&gt;
        return ModBlocks.BLOCKS.getEntries().stream().map(RegistryObject::get).toList();&lt;br /&gt;
    }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Implementing a simple subprovider===&lt;br /&gt;
The other vanilla subproviders don't have much worth extending for, so you can simply directly implement &amp;lt;code&amp;gt;Consumer&amp;lt;BiConsumer&amp;lt;ResourceLocation, LootTable.Builder&amp;gt;&amp;gt;&amp;lt;/code&amp;gt;.&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
    public void accept(BiConsumer&amp;lt;ResourceLocation, LootTable.Builder&amp;gt; consumer) {&lt;br /&gt;
        consumer.accept({ResourceLocation}, {LootTable.Builder});&lt;br /&gt;
    }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===The LootTable Builder===&lt;br /&gt;
This is where you actually make a loot table. You start with an empty &amp;lt;code&amp;gt;LootPool.Builder&amp;lt;/code&amp;gt; and add the necessary attributes to it.&lt;br /&gt;
* &amp;lt;code&amp;gt;.name&amp;lt;/code&amp;gt; is used for the pool name.&lt;br /&gt;
* &amp;lt;code&amp;gt;.setRolls&amp;lt;/code&amp;gt; is used for the amount.&lt;br /&gt;
* &amp;lt;code&amp;gt;.add&amp;lt;/code&amp;gt; is used to add an &amp;lt;code&amp;gt;LootPoolEntryContainer$Builder&amp;lt;/code&amp;gt;. You can have multiple entries.&lt;br /&gt;
&lt;br /&gt;
A &amp;lt;code&amp;gt;LootPoolEntryContainer$Builder&amp;lt;/code&amp;gt; defines what entry container is returned, and which functions and/or conditions are applied (see [https://minecraft.fandom.com/wiki/Loot_table Loot table] for the vanilla functions and conditions).&lt;br /&gt;
* &amp;lt;code&amp;gt;.when&amp;lt;/code&amp;gt; is used to apply a condition. These themselves can have multiple operations.&lt;br /&gt;
&lt;br /&gt;
After all attributes have been added the &amp;lt;code&amp;gt;LootPool.Builder&amp;lt;/code&amp;gt; can be used to make a &amp;lt;code&amp;gt;LootTable.Builder&amp;lt;/code&amp;gt;. This builder can then be used in the subproviders as discussed above.&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;LootContextParamSet&amp;lt;/code&amp;gt; is automatically applied by the vanilla &amp;lt;code&amp;gt;LootTableProvider.run&amp;lt;/code&amp;gt; method.&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
LootPool.Builder poolBuilder = LootPool.lootPool()&lt;br /&gt;
    .name(...)&lt;br /&gt;
    .setRolls(...)&lt;br /&gt;
    .add(LootItem.lootTableItem(...)&lt;br /&gt;
        .apply(function1)&lt;br /&gt;
        .apply(function2)&lt;br /&gt;
            .when(condition1)&lt;br /&gt;
            .when(condition2))&lt;br /&gt;
    );&lt;br /&gt;
LootTable.Builder tableBuilder = LootTable.lootTable().withPool(poolBuilder);&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;[[Category:Data Generation]]&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
	<entry>
		<id>https://forge.gemwire.uk/index.php?title=Dynamic_Loot_Modification&amp;diff=3326</id>
		<title>Dynamic Loot Modification</title>
		<link rel="alternate" type="text/html" href="https://forge.gemwire.uk/index.php?title=Dynamic_Loot_Modification&amp;diff=3326"/>
		<updated>2022-09-20T17:52:56Z</updated>

		<summary type="html">&lt;p&gt;Nexus-Dino: Update to 1.19 Codec GLMs&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Global Loot Modifiers are a data-driven method of handling modification of harvested drops without the need to overwrite dozens to hundreds of vanilla loot tables or to handle effects that would require interactions with another mod's loot tables without knowing what mods may be loaded. Global Loot Modifiers are also stacking, rather than last-load-wins as modifications to loot tables would be.&lt;br /&gt;
&lt;br /&gt;
== Registering a Global Loot Modifier ==&lt;br /&gt;
&lt;br /&gt;
You will need 3 things:&lt;br /&gt;
# Create a &amp;lt;code&amp;gt;global_loot_modifiers.json&amp;lt;/code&amp;gt; file at &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;/data/forge/loot_modifiers/&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;&lt;br /&gt;
#* This will tell Forge about your modifiers and works similar to [[Tags|tags]].&lt;br /&gt;
# A serialized json representing your modifier at &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;/data/&amp;lt;modID&amp;gt;/loot_modifiers/&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;&lt;br /&gt;
#* This will contain all of the data about your modification and allows data packs to tweak your effect.&lt;br /&gt;
# A class that extends &amp;lt;code&amp;gt;LootModifier&amp;lt;/code&amp;gt;&lt;br /&gt;
#* The operational code that makes your modifier work and associated serializer.&lt;br /&gt;
&lt;br /&gt;
Finally, the serializer for your operational class is [[Registration|registered]] as any other registry object.&lt;br /&gt;
&lt;br /&gt;
==The global_loot_modifiers.json==&lt;br /&gt;
All you need to add here are the file names of your loot modifiers.&lt;br /&gt;
These are the names of the json files you have made in the loot_modifiers folder, in ResourceLocation format.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;json&amp;quot;&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
  &amp;quot;replace&amp;quot;: false,&lt;br /&gt;
  &amp;quot;entries&amp;quot;: [&lt;br /&gt;
    &amp;quot;global_loot_test:silk_touch_bamboo&amp;quot;,&lt;br /&gt;
    &amp;quot;global_loot_test:smelting&amp;quot;,&lt;br /&gt;
    &amp;quot;global_loot_test:wheat_harvest&amp;quot;&lt;br /&gt;
  ]&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;code&amp;gt;replace&amp;lt;/code&amp;gt; causes the cache of modifiers to be cleared fully when this asset loads (mods are loaded in an order that may be specified by a data pack). For modders you will want to use &amp;lt;code&amp;gt;false&amp;lt;/code&amp;gt; while data pack makers may want to specify their overrides with &amp;lt;code&amp;gt;true&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;code&amp;gt;entries&amp;lt;/code&amp;gt; is an ''ordered list'' of the modifiers that will be loaded. Any modifier that is not listed will not be loaded and the ones listed are called in the order listed. This is primarily relevant to data pack makers for resolving conflicts between modifiers from separate mods.&lt;br /&gt;
&lt;br /&gt;
== The serialized json ==&lt;br /&gt;
&lt;br /&gt;
This file contains all of the potential variables related to your modifier, including the conditions that must be met prior to modifying any loot as well as any other parameters your modifier might have. Avoid hard-coded values where ever possible so that data pack makers can adjust balance if they wish to.&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;json&amp;quot;&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
  &amp;quot;conditions&amp;quot;: [&lt;br /&gt;
    {&lt;br /&gt;
      &amp;quot;condition&amp;quot;: &amp;quot;minecraft:match_tool&amp;quot;,&lt;br /&gt;
      &amp;quot;predicate&amp;quot;: {&lt;br /&gt;
        &amp;quot;item&amp;quot;: &amp;quot;minecraft:shears&amp;quot;&lt;br /&gt;
      }&lt;br /&gt;
    },&lt;br /&gt;
    {&lt;br /&gt;
      &amp;quot;condition&amp;quot;: &amp;quot;minecraft:block_state_property&amp;quot;,&lt;br /&gt;
      &amp;quot;block&amp;quot;: &amp;quot;minecraft:wheat&amp;quot;&lt;br /&gt;
    }&lt;br /&gt;
  ],&lt;br /&gt;
  &amp;quot;seedItem&amp;quot;: &amp;quot;minecraft:wheat_seeds&amp;quot;,&lt;br /&gt;
  &amp;quot;numSeeds&amp;quot;: 3,&lt;br /&gt;
  &amp;quot;replacement&amp;quot;: &amp;quot;minecraft:wheat&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In the above example, the modification only happens if the player harvests wheat when using shears (specified by the two &amp;lt;code&amp;gt;conditions&amp;lt;/code&amp;gt; which are automatically &amp;lt;code&amp;gt;AND&amp;lt;/code&amp;gt;ed together). The &amp;lt;code&amp;gt;seedsItem&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;numSeeds&amp;lt;/code&amp;gt; values are then used to count how many seeds were generated by the vanilla loot table, and if matched, are substituted for an additional &amp;lt;code&amp;gt;replacement&amp;lt;/code&amp;gt; item instead. The operation code will be shown below.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
{{Tip|&amp;lt;code&amp;gt;conditions&amp;lt;/code&amp;gt; is the only object needed by the system specification, everything else is the mod maker's data. &lt;br /&gt;
 &lt;br /&gt;
&amp;lt;code&amp;gt;seedItem&amp;lt;/code&amp;gt;, &amp;lt;code&amp;gt;numSeeds&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;replacement&amp;lt;/code&amp;gt; are NOT standard elements of Global Loot Modifiers.  &lt;br /&gt;
&lt;br /&gt;
They are deserialized manually in the next section.}}&lt;br /&gt;
&lt;br /&gt;
== The LootModifier Subclass ==&lt;br /&gt;
&lt;br /&gt;
You will also need a static child class that extends &amp;lt;code&amp;gt;GlobalLootModifierSerializer&amp;lt;T&amp;gt;&amp;lt;/code&amp;gt; where &amp;lt;code&amp;gt;T&amp;lt;/code&amp;gt; is your LootModifier subclass in order to deserialize your json data file into operational code.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;java&amp;quot;&amp;gt;&lt;br /&gt;
/**&lt;br /&gt;
     * When harvesting wheat with shears, this modifier is invoked via the wheat_harvest loot_modifier json&amp;lt;br/&amp;gt;&lt;br /&gt;
     * This modifier checks how many seeds were harvested and turns X seeds into Y wheat (3:1)&lt;br /&gt;
     *&lt;br /&gt;
     */&lt;br /&gt;
private static class WheatSeedsConverterModifier extends LootModifier&lt;br /&gt;
{&lt;br /&gt;
        public static final Supplier&amp;lt;Codec&amp;lt;WheatSeedsConverterModifier&amp;gt;&amp;gt; CODEC = Suppliers.memoize(() -&amp;gt; &lt;br /&gt;
        RecordCodecBuilder.create(inst -&amp;gt; codecStart(inst).and(&lt;br /&gt;
                inst.group(&lt;br /&gt;
                        Codec.INT.fieldOf(&amp;quot;numSeeds&amp;quot;).forGetter(m -&amp;gt; m.numSeedsToConvert),&lt;br /&gt;
                        ForgeRegistries.ITEMS.getCodec().fieldOf(&amp;quot;seedItem&amp;quot;).forGetter(m -&amp;gt; m.itemToCheck),&lt;br /&gt;
                        ForgeRegistries.ITEMS.getCodec().fieldOf(&amp;quot;replacement&amp;quot;).forGetter(m -&amp;gt; m.itemReward)&lt;br /&gt;
                )).apply(inst, WheatSeedsConverterModifier::new)&lt;br /&gt;
        ));&lt;br /&gt;
&lt;br /&gt;
        private final int numSeedsToConvert;&lt;br /&gt;
        private final Item itemToCheck;&lt;br /&gt;
        private final Item itemReward;&lt;br /&gt;
        public WheatSeedsConverterModifier(LootItemCondition[] conditionsIn, int numSeeds, Item itemCheck, &lt;br /&gt;
             Item reward)&lt;br /&gt;
        {&lt;br /&gt;
            super(conditionsIn);&lt;br /&gt;
            numSeedsToConvert = numSeeds;&lt;br /&gt;
            itemToCheck = itemCheck;&lt;br /&gt;
            itemReward = reward;&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @NotNull&lt;br /&gt;
        @Override&lt;br /&gt;
        public ObjectArrayList&amp;lt;ItemStack&amp;gt; doApply(ObjectArrayList&amp;lt;ItemStack&amp;gt; generatedLoot, LootContext context) {&lt;br /&gt;
            //&lt;br /&gt;
            // Additional conditions can be checked, though as much as possible should be parameterized via JSON data.&lt;br /&gt;
            // It is better to write a new ILootCondition implementation than to do things here.&lt;br /&gt;
            //&lt;br /&gt;
            int numSeeds = 0;&lt;br /&gt;
            generatedLoot.stream().filter(stack -&amp;gt; stack.getItem() == itemToCheck)&lt;br /&gt;
                   .forEach(stack -&amp;gt; numSeeds+=stack.getCount())&lt;br /&gt;
            if(numSeeds &amp;gt;= numSeedsToConvert) {&lt;br /&gt;
                generatedLoot.removeIf(x -&amp;gt; x.getItem() == itemToCheck);&lt;br /&gt;
                generatedLoot.add(new ItemStack(itemReward, (numSeeds/numSeedsToConvert)));&lt;br /&gt;
                numSeeds = numSeeds%numSeedsToConvert;&lt;br /&gt;
                if(numSeeds &amp;gt; 0)&lt;br /&gt;
                    generatedLoot.add(new ItemStack(itemToCheck, numSeeds));&lt;br /&gt;
            }&lt;br /&gt;
            return generatedLoot;&lt;br /&gt;
        }&lt;br /&gt;
&lt;br /&gt;
        @Override&lt;br /&gt;
        public Codec&amp;lt;? extends IGlobalLootModifier&amp;gt; codec() {&lt;br /&gt;
            return CODEC.get();&lt;br /&gt;
        }&lt;br /&gt;
    }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The critical portion is the &amp;lt;code&amp;gt;doApply&amp;lt;/code&amp;gt; method.&lt;br /&gt;
&lt;br /&gt;
This method is only called if the &amp;lt;code&amp;gt;conditions&amp;lt;/code&amp;gt; specified return &amp;lt;code&amp;gt;true&amp;lt;/code&amp;gt; and the modder is now able to make the modifications they desire. In this case we can see that the number of &amp;lt;code&amp;gt;itemToCheck&amp;lt;/code&amp;gt; meets or exceeds the &amp;lt;code&amp;gt;numSeedsToConvert&amp;lt;/code&amp;gt; before modifying the list by adding an &amp;lt;code&amp;gt;itemReward&amp;lt;/code&amp;gt; and removing any excess &amp;lt;code&amp;gt;itemToCheck&amp;lt;/code&amp;gt; stacks, matching the previously mentioned effects: ''When a wheat block is harvested with shears, if enough seeds are generated as loot, they are converted to additional wheat instead''.&lt;br /&gt;
&lt;br /&gt;
Utilize &amp;lt;code&amp;gt;GlobalLootModifierProvider&amp;lt;/code&amp;gt; for [[datageneration|data generation]].&lt;br /&gt;
&lt;br /&gt;
Additional [https://github.com/MinecraftForge/MinecraftForge/blob/1.19.x/src/test/java/net/minecraftforge/debug/gameplay/loot/GlobalLootModifiersTest.java examples] can be found on the Forge Git repository, including silk touch and smelting effects.&lt;/div&gt;</summary>
		<author><name>Nexus-Dino</name></author>
	</entry>
</feed>