Two Ways to Render a Block
Bedrock Edition supports two distinct pipelines for rendering custom blocks. Regardless of which pipeline you choose, your actual PNG image files always live in the resource pack, and they are always given short alias names inside `RP/textures/terrain_texture.json`. Where the two pipelines differ is how the game decides which model and which texture alias to apply to your block.
The first pipeline is the legacy `RP/blocks.json` method. In this setup, the behavior pack file contains no visual components at all. Instead, you open `RP/blocks.json` in your resource pack and assign textures and a sound type to your block identifier. This method is simple and lets you easily apply distinct textures to the top, bottom, and sides of a standard cube, as well as an isotropic random rotation. However, it cannot react to block states or permutations.
The second pipeline is the component-based method, which uses `minecraft:geometry` and `minecraft:material_instances` directly inside your behavior pack block JSON. The moment you add `minecraft:geometry` or `minecraft:material_instances` to a block, the game switches that block to the modern rendering pipeline. In this mode, texture definitions inside `RP/blocks.json` are ignored for that block, though `RP/blocks.json` is still often used to assign the block's step and breaking sounds.
Registering Texture Shortnames
Before you can reference a texture in either pipeline, you must register a shortname for it in `RP/textures/terrain_texture.json`. The game does not allow you to type file paths like `textures/blocks/my_block.png` directly into a block definition. Instead, you map a short string key to the file path inside the `texture_data` object.
Keep your shortnames prefixed with your pack namespace or studio initials so they do not collide with vanilla shortnames or other add-ons loaded in the same world. Note that file paths in this file omit the `.png` file extension.
{
"resource_pack_name": "wiki_pack",
"texture_name": "atlas.terrain",
"padding": 8,
"num_mip_levels": 4,
"texture_data": {
"wiki_crate_top": {
"textures": "textures/blocks/crate_top"
},
"wiki_crate_side": {
"textures": "textures/blocks/crate_side"
}
}
}The Resource Pack Pipeline (RP/blocks.json)
If you just need a standard 16x16x16 opaque cube that never changes its appearance via block states, configuring it in `RP/blocks.json` is very fast. You match the block's full identifier (including namespace) and supply a `textures` key and a `sound` key.
The `textures` property can be a single string shortname if all six faces are identical, or an object specifying `up`, `down`, and `side` (or `north`, `south`, `east`, `west`). If you use this pipeline, make sure your behavior pack block file does not include `minecraft:geometry` or `minecraft:material_instances`.
{
"format_version": [1, 1, 0],
"wiki:wooden_crate": {
"textures": {
"up": "wiki_crate_top",
"down": "wiki_crate_top",
"side": "wiki_crate_side"
},
"sound": "wood"
}
}The Component Pipeline (Geometry and Materials)
When you want a custom 3D model from Blockbench, transparency, unlit faces, or textures that swap when a block state changes, you must use the component pipeline inside your behavior pack `BP/blocks/` file. This requires two components working as a pair: `minecraft:geometry` and `minecraft:material_instances`.
If you want a standard full cube while using the component pipeline—for example, so you can swap its texture in a permutation—you do not need to make a custom model file. You can use the built-in vanilla identifier `minecraft:geometry.full_block`. For custom models, place your `.geo.json` file in `RP/models/blocks/` and reference its `description.identifier` string (which must start with `geometry.`).
The `minecraft:material_instances` component maps the material names requested by the geometry to the texture shortnames you defined in `terrain_texture.json`. The wildcard key `*` acts as the default fallback for any face that does not have a specific material name assigned, and it is also used by the game for breaking particles.
{
"format_version": "1.20.80",
"minecraft:block": {
"description": {
"identifier": "wiki:custom_lantern"
},
"components": {
"minecraft:geometry": "minecraft:geometry.full_block",
"minecraft:material_instances": {
"*": {
"texture": "wiki_crate_side",
"render_method": "alpha_test",
"face_dimming": true,
"ambient_occlusion": true
}
}
}
}
}Material Instance Settings and Render Methods
Inside `minecraft:material_instances`, each named instance (such as `*`) takes an object that controls how the game shader draws those polygons. Choosing the right `render_method` is essential for performance and visual accuracy. Using a transparent render method when your texture is completely solid wastes rendering performance and can cause sorting glitches.
| Field / Value | What it does | Notes |
|---|---|---|
| texture | Links to the shortname in terrain_texture.json | Required on the '*' instance unless referencing another instance name. |
| render_method: "opaque" | Renders solid pixels with no transparency | Default method. Culls adjacent solid block faces. |
| render_method: "alpha_test" | Pixels are either 100% solid or 100% invisible | Use for grates, leaves, cross-shaped plants, and cutout windows. |
| render_method: "blend" | Supports partial translucency like stained glass | Most expensive to render; can cause depth-sorting issues with water or other blend blocks. |
| render_method: "double_sided" | Renders both front and back of solid polygons | No transparency support. For flat planes with cutouts, use alpha_test models with 0-thickness cubes instead. |
| ambient_occlusion | Boolean controlling soft corner shadows | Defaults to true. Set to false on glowing blocks or flat plant models. |
| face_dimming | Boolean controlling directional shading | Defaults to true (bottom face is darkest, top is brightest). Set to false for evenly lit blocks. |
Culling and Lighting with Custom Geometry
When you assign a `minecraft:geometry` component—even if it is `minecraft:geometry.full_block`—the game treats your block differently for lighting and face culling than it treats a legacy block. If your custom model is smaller than a full 16x16x16 cube, or if it uses `alpha_test` or `blend`, you must configure how light passes through it.
By default, custom blocks may block sky light or cause adjacent blocks to turn black where they touch. Add the `minecraft:light_dampening` component and set it to `0` on non-full blocks (like lanterns, fences, or custom furniture) so they do not cast dark shadow blotches onto the floor beneath them. Only leave light dampening at the default value of `15` for complete, solid opaque cubes.
Which versions this applies to
Applies to Bedrock Edition 1.19.50 and newer (format_version 1.19.50+ through 1.21.x). Both `minecraft:geometry` (including `minecraft:geometry.full_block`) and `minecraft:material_instances` are stable and require no experimental toggles.
When it does not work
| What you see | Why | The fix |
|---|---|---|
| The block renders with the magenta and black missing texture checkerboard. | The string inside `texture` in `minecraft:material_instances` (or `RP/blocks.json`) does not match any key inside `RP/textures/terrain_texture.json`, or the PNG file path inside `terrain_texture.json` is misspelled. | Verify that the shortname matches character-for-character between your block definition and `terrain_texture.json`, and confirm the PNG file exists at the exact path specified. |
| Per-face textures (`up`, `down`, `side`) defined in `RP/blocks.json` are completely ignored. | Your behavior pack block JSON includes `minecraft:geometry` or `minecraft:material_instances`. Using either component overrides `RP/blocks.json` texture assignments. | Either remove the visual components from the behavior pack to use the legacy pipeline, or define named material instances on your geometry's faces and map them inside `minecraft:material_instances`. |
| Content Log shows `[Blocks][error] ... minecraft:material_instances is missing required '*' instance` or breaking particles look like dirt/missing textures. | You defined specific material names for your model's bones or faces inside `minecraft:material_instances`, but forgot to include the fallback `"*"` key. | Always include a `"*"` object inside `minecraft:material_instances`. Even if every face on your Blockbench model uses a custom material name, the game requires `"*"` as the default fallback and for block destruction particles. |
| Transparent parts of a texture render as solid black or white. | The material instance is using the default `"opaque"` render method, which discards the alpha channel of your PNG. | Set `"render_method": "alpha_test"` for hard cutouts or `"render_method": "blend"` for semi-transparent pixels inside `minecraft:material_instances`. |
Reference, straight from the game files
Read out of the game itself, so the ids match the version you are building for.
