Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
44e0f2d
[FRAPI] initial port to 1.21.11
sylv256 Dec 10, 2025
86107e5
fix: get the game running lol
sylv256 Dec 10, 2025
9eb55f5
fix: implement `IndigoRenderer#renderBlockAsEntity`
sylv256 Dec 10, 2025
9f8b37a
fix: access modifier in `SectionCompilerMixin`
sylv256 Dec 11, 2025
9bc8b15
refactor!: remove unused vanilla quad vertex format fields
sylv256 Dec 11, 2025
97747fe
fix: accidentally overwriting indigo's vertex data array
sylv256 Dec 11, 2025
7c8252b
fix: clean up `UnbakedModelDeserializerTest`, add more descriptive FIXME
sylv256 Dec 11, 2025
e29b07a
feat: `QuadAtlas`
sylv256 Dec 11, 2025
b923104
Revert "fix: clean up `UnbakedModelDeserializerTest`, add more descri…
sylv256 Dec 11, 2025
034aa53
fix: set `BlockModelWrapper#renderType` to the block render type when…
sylv256 Dec 11, 2025
2961ce0
chore: fix checkstyle issues
sylv256 Dec 11, 2025
831c9b2
docs: re-add documentation on `MutableQuadView#color(int, int)`
sylv256 Dec 11, 2025
3c8756b
refactor!: `Function<QuadAtlas, SpriteFinder>` -> `QuadAtlasSpriteGet…
sylv256 Dec 11, 2025
f4b7f4b
fix: 100% restore removed code from `FrameBlockStateModel`
sylv256 Dec 11, 2025
b464a98
Merge branch '1.21.11' into rendering-1
sylv256 Dec 11, 2025
b672ff6
chore: run spotlessApply
sylv256 Dec 12, 2025
6ebd2a7
Port fixes/improvements
PepperCode1 Dec 13, 2025
ad0116b
feat: `FabricLayerRenderState#setRenderTypeGetter` & `ItemLayerRender…
sylv256 Dec 16, 2025
0ab57f9
refactor: ~minimize the jank~
sylv256 Dec 16, 2025
cbfe3d2
chore: remove unnecessary `BAKED_GEOMETRY` map
sylv256 Dec 16, 2025
2be0f7b
feat(test): glass testing
sylv256 Dec 16, 2025
8d5a323
More fixes/improvements
PepperCode1 Dec 16, 2025
a273d6a
Improve test mod
PepperCode1 Dec 17, 2025
2a5af0d
Validate quad atlases of mesh in SimpleModelWrapper.bake
PepperCode1 Dec 17, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@
import net.fabricmc.fabric.api.renderer.v1.render.FabricBlockModelRenderer;
import net.fabricmc.fabric.api.renderer.v1.render.FabricBlockRenderManager;
import net.fabricmc.fabric.api.renderer.v1.render.FabricLayerRenderState;
import net.fabricmc.fabric.api.renderer.v1.render.ItemRenderTypeGetter;
import net.fabricmc.fabric.impl.renderer.RendererManager;

/**
Expand Down Expand Up @@ -114,4 +115,10 @@ static void register(Renderer renderer) {
*/
@ApiStatus.OverrideOnly
QuadEmitter getLayerRenderStateEmitter(ItemStackRenderState.LayerRenderState layer);

/**
* @see FabricLayerRenderState#setRenderTypeGetter(ItemRenderTypeGetter)
*/
@ApiStatus.OverrideOnly
void setLayerRenderTypeGetter(ItemStackRenderState.LayerRenderState layer, ItemRenderTypeGetter renderTypeGetter);
}
Original file line number Diff line number Diff line change
Expand Up @@ -23,16 +23,17 @@
import org.jspecify.annotations.Nullable;

import net.minecraft.client.Minecraft;
import net.minecraft.client.renderer.ItemBlockRenderTypes;
import net.minecraft.client.renderer.block.model.BakedQuad;
import net.minecraft.client.renderer.chunk.ChunkSectionLayer;
import net.minecraft.client.renderer.item.ItemStackRenderState;
import net.minecraft.client.renderer.rendertype.RenderType;
import net.minecraft.client.renderer.rendertype.RenderTypes;
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
import net.minecraft.core.Direction;
import net.minecraft.world.level.block.state.BlockState;

import net.fabricmc.fabric.api.renderer.v1.render.RenderLayerHelper;
import net.fabricmc.fabric.api.renderer.v1.render.FabricLayerRenderState;
import net.fabricmc.fabric.api.renderer.v1.render.ItemRenderTypeGetter;
import net.fabricmc.fabric.api.util.TriState;
import net.fabricmc.fabric.impl.renderer.QuadSpriteBaker;

Expand Down Expand Up @@ -181,12 +182,19 @@ default MutableQuadView uv(int vertexIndex, Vector2fc uv) {
}

/**
* Sets the texture coordinates for all vertices using the given sprite. Can handle UV locking, rotation,
* interpolation, etc. Control this behavior by passing additive combinations of the BAKE_ flags defined in this
* interface.
* Sets the texture coordinates for all vertices using the given sprite. Also sets this quad's atlas to the given
* sprite's atlas. Can handle UV locking, rotation, interpolation, etc. Control this behavior by passing additive
* combinations of the BAKE_ flags defined in this interface.
*/
default MutableQuadView spriteBake(TextureAtlasSprite sprite, int bakeFlags) {
QuadSpriteBaker.bakeSprite(this, sprite, bakeFlags);
QuadAtlas atlas = QuadAtlas.of(sprite.atlasLocation());

if (atlas == null) {
atlas = QuadAtlas.BLOCK;
}

atlas(atlas);
return this;
}

Expand Down Expand Up @@ -272,13 +280,11 @@ default MutableQuadView normal(int vertexIndex, Vector3fc normal) {
/**
* Controls how this quad's pixels should be blended with the scene.
*
* <p>If set to {@code null}, {@link RenderTypes#getBlockLayer(BlockState)} will be used to retrieve the render
* layer in block contexts and
* {@linkplain ItemStackRenderState.LayerRenderState#setRenderType(RenderType)} the render layer of the state layer}
* will be used in item contexts. Set to another value to override this behavior.
* <p>If set to {@code null}, {@link ItemBlockRenderTypes#getChunkRenderType(BlockState)} will be used to retrieve
* the render layer in block contexts. Set to another value to override this behavior.
*
* <p>In block contexts, a non-null value will be used directly. In item contexts, a non-null value will be
* converted to a {@link RenderType} using {@link RenderLayerHelper#getEntityBlockLayer(ChunkSectionLayer)}.
* <p>In block contexts, a non-null value will be used directly. In item contexts, any value will be converted to a
* {@link RenderType} using {@link FabricLayerRenderState#setRenderTypeGetter(ItemRenderTypeGetter)}.
*
* <p>The default value is {@code null}.
*/
Expand Down Expand Up @@ -348,6 +354,18 @@ default MutableQuadView normal(int vertexIndex, Vector3fc normal) {
*/
MutableQuadView shadeMode(ShadeMode mode);

/**
* Sets the {@linkplain QuadAtlas atlas texture} used by this quad.
*
* <p>In block contexts, this property must be {@link QuadAtlas#BLOCK}. In item contexts, this property will be
* converted to a {@link RenderType} using {@link FabricLayerRenderState#setRenderTypeGetter(ItemRenderTypeGetter)}.
*
* <p>The default value is {@link QuadAtlas#BLOCK}.
*
* @see QuadAtlas
*/
MutableQuadView atlas(QuadAtlas quadAtlas);

/**
* Sets the tint index, which is used to retrieve the tint color.
*
Expand All @@ -371,22 +389,8 @@ default MutableQuadView normal(int vertexIndex, Vector3fc normal) {
MutableQuadView copyFrom(QuadView quad);

/**
* Sets this quad's vertex data for all vertices using data in given array, starting at the given index. The array
* must have at least {@link #VANILLA_QUAD_STRIDE} elements starting at the given index. The format of the data must
* be the same as {@link BakedQuad#vertices()}. This quad's lightmap values and normals will be set even though
* vanilla does not decode them from packed vertex data.
*
* <p>Prefer using {@link #fromBakedQuad(BakedQuad)} instead if you have a {@link BakedQuad}.
*
* <p>Calling this method does not emit this quad.
*/
MutableQuadView fromVanilla(int[] vertexData, int startIndex);

/**
* Sets all applicable data and properties of this quad as specified by the given {@link BakedQuad}. This quad's
* lightmap values and normals will be set even though vanilla does not decode them from packed vertex data. The
* {@linkplain BakedQuad#lightEmission() baked quad's light emission} will be applied to the lightmap values from
* the vertex data after copying.
* Sets all applicable data and properties of this quad as specified by the given {@link BakedQuad}. In addition,
* this quad's vertex colors and vertex normals will be reset. This quad's existing lightmap values will be ignored.
*
* <p>Calling this method does not emit this quad.
*/
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
/*
* Copyright (c) 2016, 2017, 2018, 2019 FabricMC
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package net.fabricmc.fabric.api.renderer.v1.mesh;

import org.jspecify.annotations.Nullable;

import net.minecraft.client.renderer.texture.TextureAtlas;
import net.minecraft.resources.Identifier;

/**
* An atlas texture that a {@link QuadView} uses.
*/
public enum QuadAtlas {
BLOCK(TextureAtlas.LOCATION_BLOCKS),
ITEM(TextureAtlas.LOCATION_ITEMS);

private final Identifier textureId;

QuadAtlas(Identifier textureId) {
this.textureId = textureId;
}

/**
* {@return the quad atlas for the given atlas texture ID or null if no corresponding quad atlas exists}
*/
@Nullable
public static QuadAtlas of(Identifier atlasTextureId) {
if (atlasTextureId.equals(TextureAtlas.LOCATION_BLOCKS)) {
return BLOCK;
} else if (atlasTextureId.equals(TextureAtlas.LOCATION_ITEMS)) {
return ITEM;
} else {
return null;
}
}

/**
* {@return the atlas texture ID}
*/
public Identifier getTextureId() {
return textureId;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,9 @@ default QuadEmitter normal(int vertexIndex, Vector3fc normal) {
@Override
QuadEmitter shadeMode(ShadeMode mode);

@Override
QuadEmitter atlas(QuadAtlas quadAtlas);

@Override
QuadEmitter tintIndex(int tintIndex);

Expand All @@ -150,9 +153,6 @@ default QuadEmitter normal(int vertexIndex, Vector3fc normal) {
@Override
QuadEmitter copyFrom(QuadView quad);

@Override
QuadEmitter fromVanilla(int[] vertexData, int startIndex);

@Override
QuadEmitter fromBakedQuad(BakedQuad quad);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,12 @@

package net.fabricmc.fabric.api.renderer.v1.mesh;

import com.mojang.blaze3d.vertex.DefaultVertexFormat;
import org.joml.Vector2f;
import org.joml.Vector3f;
import org.joml.Vector3fc;
import org.jspecify.annotations.Nullable;

import net.minecraft.client.model.geom.builders.UVPair;
import net.minecraft.client.renderer.LightTexture;
import net.minecraft.client.renderer.block.model.BakedQuad;
import net.minecraft.client.renderer.chunk.ChunkSectionLayer;
Expand All @@ -33,23 +33,17 @@
import net.fabricmc.fabric.api.util.TriState;

/**
* Interface for reading quad data encoded in {@link Mesh}es.
* Interface for reading quad data encoded in {@linkplain Mesh Meshes}.
* Enables models to do analysis, re-texturing or translation without knowing the
* renderer's vertex formats and without retaining redundant information.
*
* <p>Unless otherwise stated, assume all properties persist through serialization into {@link Mesh}es and have an
* <p>Unless otherwise stated, assume all properties persist through serialization into {@linkplain Mesh Meshes} and have an
* effect in both block and item contexts. If a property is described as transient, then its value will not persist
* through serialization into a {@link Mesh}.
*
* <p>Only the renderer should implement or extend this interface.
*/
public interface QuadView {
/** Count of integers in a conventional (un-modded) block or item vertex. */
int VANILLA_VERTEX_STRIDE = DefaultVertexFormat.BLOCK.getVertexSize() / 4;

/** Count of integers in a conventional (un-modded) block or item quad. */
int VANILLA_QUAD_STRIDE = VANILLA_VERTEX_STRIDE * 4;

/**
* Gets the X coordinate of the geometric position of the given vertex.
*/
Expand Down Expand Up @@ -193,6 +187,11 @@ public interface QuadView {
*/
ShadeMode shadeMode();

/**
* @see MutableQuadView#atlas(QuadAtlas)
*/
QuadAtlas atlas();

/**
* This method is equivalent to {@link BakedQuad#tintIndex()}.
*
Expand All @@ -205,24 +204,21 @@ public interface QuadView {
*/
int tag();

/**
* Outputs this quad's vertex data into the given array, starting at the given index. The array must have at least
* {@link #VANILLA_QUAD_STRIDE} elements available starting at the given index. The format of the data is the same
* as {@link BakedQuad#vertices()}. Lightmap values and normals will be populated even though vanilla does not use
* them.
*/
void toVanilla(int[] target, int startIndex);

/**
* Creates a new {@link BakedQuad} with an appearance as close as possible to this quad, as permitted by vanilla.
* Vertex lightmap values and vertex normals will be populated even though vanilla does not use them.
*
* @param sprite The sprite is not serialized so it must be provided by the caller. Retrieve it using
* {@link SpriteFinder#find(QuadView)} if it is not already known.
*/
default BakedQuad toBakedQuad(TextureAtlasSprite sprite) {
int[] vertexData = new int[VANILLA_QUAD_STRIDE];
toVanilla(vertexData, 0);
Vector3f position0 = copyPos(0, null);
Vector3f position1 = copyPos(1, null);
Vector3f position2 = copyPos(2, null);
Vector3f position3 = copyPos(3, null);
long packedUV0 = UVPair.pack(u(0), v(0));
long packedUV1 = UVPair.pack(u(1), v(1));
long packedUV2 = UVPair.pack(u(2), v(2));
long packedUV3 = UVPair.pack(u(3), v(3));

// The light emission is set to 15 if the quad is emissive; otherwise, to the minimum of all four sky light
// values and all four block light values.
Expand All @@ -243,6 +239,20 @@ default BakedQuad toBakedQuad(TextureAtlasSprite sprite) {
}
}

return new BakedQuad(vertexData, tintIndex(), lightFace(), sprite, diffuseShade(), lightEmission);
return new BakedQuad(
position0,
position1,
position2,
position3,
packedUV0,
packedUV1,
packedUV2,
packedUV3,
tintIndex(),
lightFace(),
sprite,
diffuseShade(),
lightEmission
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@
import net.minecraft.core.Direction;

import net.fabricmc.fabric.api.renderer.v1.mesh.QuadTransform;
import net.fabricmc.fabric.api.renderer.v1.sprite.SpriteFinderGetter;

/**
* Utilities to make it easier to work with {@link ModelState}.
Expand Down Expand Up @@ -178,7 +179,7 @@ public Matrix4fc inverseFaceTransformation(Direction face) {
* <p>This method is most useful when creating custom implementations of {@link UnbakedGeometry}, which receive a
* {@link ModelState}.
*/
public static QuadTransform asQuadTransform(ModelState settings, SpriteFinder spriteFinder) {
public static QuadTransform asQuadTransform(ModelState settings, SpriteFinderGetter spriteFinderGetter) {
Matrix4fc matrix = settings.transformation().getMatrix();

// Assumes face transformations are identity if main transformation is identity
Expand All @@ -196,6 +197,7 @@ public static QuadTransform asQuadTransform(ModelState settings, SpriteFinder sp
Matrix4fc reverseMatrix = settings.inverseFaceTransformation(lightFace);

if (!MatrixUtil.isIdentity(reverseMatrix)) {
SpriteFinder spriteFinder = spriteFinderGetter.spriteFinder(quad.atlas());
TextureAtlasSprite sprite = spriteFinder.find(quad);

for (int vertexIndex = 0; vertexIndex < 4; vertexIndex++) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,6 @@
import net.minecraft.client.renderer.MultiBufferSource;
import net.minecraft.client.renderer.block.BlockRenderDispatcher;
import net.minecraft.client.renderer.block.model.BlockStateModel;
import net.minecraft.client.renderer.special.SpecialModelRenderer;
import net.minecraft.core.BlockPos;
import net.minecraft.util.RandomSource;
import net.minecraft.world.level.BlockAndTintGetter;
Expand All @@ -45,8 +44,8 @@ public interface FabricBlockRenderManager {
* necessary. <b>Prefer using this method over the vanilla alternative to correctly buffer models that have geometry
* on multiple render layers and to provide the model with additional context.</b>
*
* <p>This method allows buffering a block model with minimal transformations to the model geometry. Also invokes
* the {@link SpecialModelRenderer}. Usually used by entity renderers.
* <p>This method allows buffering a block model with minimal transformations to the model geometry. Usually used by
* entity renderers.
*
* @param state The block state.
* @param matrices The matrices.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import java.util.function.Supplier;

import net.minecraft.client.renderer.item.ItemStackRenderState;
import net.minecraft.client.renderer.rendertype.RenderType;

import net.fabricmc.fabric.api.renderer.v1.Renderer;
import net.fabricmc.fabric.api.renderer.v1.mesh.QuadEmitter;
Expand All @@ -45,4 +46,20 @@ public interface FabricLayerRenderState {
default QuadEmitter emitter() {
return Renderer.get().getLayerRenderStateEmitter((ItemStackRenderState.LayerRenderState) this);
}

/**
* Sets the function that chooses the {@link RenderType} for quads added to this layer through {@link #emitter()}
* based on certain quad properties. This method has no effect on how
* {@linkplain ItemStackRenderState.LayerRenderState#prepareQuadList() vanilla quads} are rendered. If this function
* is not set, all non-vanilla quads in this layer will be rendered using this layer's
* {@linkplain ItemStackRenderState.LayerRenderState#setRenderType(RenderType) default render type}. If the
* function returns {@code null} for a certain combination of quad properties, then all non-vanilla quads with
* matching property values will use this layer's default render type. This layer's function will be unset on
* {@link ItemStackRenderState.LayerRenderState#clear()}.
*
* @see ItemRenderTypeGetter
*/
default void setRenderTypeGetter(ItemRenderTypeGetter renderTypeGetter) {
Renderer.get().setLayerRenderTypeGetter((ItemStackRenderState.LayerRenderState) this, renderTypeGetter);
}
}
Loading
Loading