mirror of
https://github.com/FabricMC/fabric.git
synced 2024-11-14 19:25:23 -05:00
Fix #1273 (Make MultipartBakedModel and WeightedBackedModel implement FabricBakedModel properly) (#1301)
* fix #1273 * Expand testmod to test multipart and weighted models with FRAPI submodels Co-authored-by: Technici4n <13494793+Technici4n@users.noreply.github.com>
This commit is contained in:
parent
be9da31056
commit
8a5c621a87
15 changed files with 261 additions and 20 deletions
4
.gitignore
vendored
4
.gitignore
vendored
|
@ -1,6 +1,10 @@
|
|||
# Gradle
|
||||
.gradle
|
||||
|
||||
# VSCode
|
||||
.settings/
|
||||
.vscode/
|
||||
|
||||
# Eclipse
|
||||
.checkstyle
|
||||
.classpath
|
||||
|
|
|
@ -20,10 +20,10 @@ def ENV = System.getenv()
|
|||
|
||||
class Globals {
|
||||
static def baseVersion = "0.34.9"
|
||||
static def mcVersion = "1.17-rc1"
|
||||
static def yarnVersion = "+build.5"
|
||||
static def mcVersion = "1.17"
|
||||
static def yarnVersion = "+build.6"
|
||||
static def loaderVersion = "0.11.3"
|
||||
static def preRelease = true
|
||||
static def preRelease = false
|
||||
}
|
||||
|
||||
version = Globals.baseVersion + "+" + (ENV.GITHUB_RUN_NUMBER ? "" : "local-") + getBranch()
|
||||
|
|
|
@ -10,5 +10,9 @@ dependencies {
|
|||
testmodImplementation project(path: ':fabric-models-v0', configuration: 'dev')
|
||||
testmodImplementation project(path: ':fabric-networking-blockentity-v0', configuration: 'dev')
|
||||
testmodImplementation project(path: ':fabric-object-builder-api-v1', configuration: 'dev')
|
||||
testmodImplementation project(path: ':fabric-renderer-indigo', configuration: 'dev')
|
||||
testmodImplementation project(path: ':fabric-rendering-data-attachment-v1', configuration: 'dev')
|
||||
testmodImplementation project(path: ':fabric-resource-loader-v0', configuration: 'dev')
|
||||
testmodImplementation project(path: ':fabric-tag-extensions-v0', configuration: 'dev')
|
||||
testmodImplementation project(path: ':fabric-tool-attribute-api-v1', configuration: 'dev')
|
||||
}
|
||||
|
|
|
@ -0,0 +1,101 @@
|
|||
/*
|
||||
* 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.mixin.renderer.client;
|
||||
|
||||
import java.util.BitSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Random;
|
||||
import java.util.function.Predicate;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.apache.commons.lang3.tuple.Pair;
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.Unique;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.client.render.model.BakedModel;
|
||||
import net.minecraft.client.render.model.MultipartBakedModel;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.world.BlockRenderView;
|
||||
|
||||
import net.fabricmc.fabric.api.renderer.v1.model.FabricBakedModel;
|
||||
import net.fabricmc.fabric.api.renderer.v1.render.RenderContext;
|
||||
|
||||
@Mixin(MultipartBakedModel.class)
|
||||
public class MixinMultipartBakedModel implements FabricBakedModel {
|
||||
@Shadow
|
||||
@Final
|
||||
private List<Pair<Predicate<BlockState>, BakedModel>> components;
|
||||
|
||||
@Shadow
|
||||
@Final
|
||||
private Map<BlockState, BitSet> stateCache;
|
||||
|
||||
@Unique
|
||||
boolean isVanilla = true;
|
||||
|
||||
@Override
|
||||
public boolean isVanillaAdapter() {
|
||||
return isVanilla;
|
||||
}
|
||||
|
||||
@Inject(at = @At("RETURN"), method = "<init>")
|
||||
private void onInit(List<Pair<Predicate<BlockState>, BakedModel>> components, CallbackInfo cb) {
|
||||
for (Pair<Predicate<BlockState>, BakedModel> component : components) {
|
||||
if (!((FabricBakedModel) component.getRight()).isVanillaAdapter()) {
|
||||
isVanilla = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void emitBlockQuads(BlockRenderView blockView, BlockState state, BlockPos pos, Supplier<Random> randomSupplier, RenderContext context) {
|
||||
BitSet bitSet = this.stateCache.get(state);
|
||||
|
||||
if (bitSet == null) {
|
||||
bitSet = new BitSet();
|
||||
|
||||
for (int i = 0; i < this.components.size(); i++) {
|
||||
Pair<Predicate<BlockState>, BakedModel> pair = components.get(i);
|
||||
|
||||
if (pair.getLeft().test(state)) {
|
||||
((FabricBakedModel) pair.getRight()).emitBlockQuads(blockView, state, pos, randomSupplier, context);
|
||||
bitSet.set(i);
|
||||
}
|
||||
}
|
||||
|
||||
stateCache.put(state, bitSet);
|
||||
} else {
|
||||
for (int i = 0; i < this.components.size(); i++) {
|
||||
if (bitSet.get(i)) ((FabricBakedModel) components.get(i).getRight()).emitBlockQuads(blockView, state, pos, randomSupplier, context);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void emitItemQuads(ItemStack stack, Supplier<Random> randomSupplier, RenderContext context) {
|
||||
// Vanilla doesn't use MultipartBakedModel for items.
|
||||
}
|
||||
}
|
|
@ -0,0 +1,86 @@
|
|||
/*
|
||||
* 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.mixin.renderer.client;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Random;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.Unique;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.client.render.model.BakedModel;
|
||||
import net.minecraft.client.render.model.WeightedBakedModel;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.collection.Weighted;
|
||||
import net.minecraft.util.collection.Weighting;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.world.BlockRenderView;
|
||||
|
||||
import net.fabricmc.fabric.api.renderer.v1.model.FabricBakedModel;
|
||||
import net.fabricmc.fabric.api.renderer.v1.render.RenderContext;
|
||||
|
||||
@Mixin(WeightedBakedModel.class)
|
||||
public class MixinWeightedBakedModel implements FabricBakedModel {
|
||||
@Shadow
|
||||
@Final
|
||||
private int totalWeight;
|
||||
@Shadow
|
||||
@Final
|
||||
private List<Weighted.Present<BakedModel>> models;
|
||||
@Unique
|
||||
boolean isVanilla = true;
|
||||
|
||||
@Inject(at = @At("RETURN"), method = "<init>")
|
||||
private void onInit(List<Weighted.Present<BakedModel>> models, CallbackInfo cb) {
|
||||
for (int i = 0; i < models.size(); i++) {
|
||||
if (!((FabricBakedModel) models.get(i).getData()).isVanillaAdapter()) {
|
||||
isVanilla = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isVanillaAdapter() {
|
||||
return isVanilla;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void emitBlockQuads(BlockRenderView blockView, BlockState state, BlockPos pos, Supplier<Random> randomSupplier, RenderContext context) {
|
||||
Weighted.Present<BakedModel> selected = Weighting.getAt(this.models, Math.abs((int) randomSupplier.get().nextLong()) % this.totalWeight).orElse(null);
|
||||
|
||||
if (selected != null) {
|
||||
((FabricBakedModel) selected.getData()).emitBlockQuads(blockView, state, pos, randomSupplier, context);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void emitItemQuads(ItemStack stack, Supplier<Random> randomSupplier, RenderContext context) {
|
||||
Weighted.Present<BakedModel> selected = Weighting.getAt(this.models, Math.abs((int) randomSupplier.get().nextLong()) % this.totalWeight).orElse(null);
|
||||
|
||||
if (selected != null) {
|
||||
((FabricBakedModel) selected.getData()).emitItemQuads(stack, randomSupplier, context);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -14,7 +14,7 @@
|
|||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package net.fabricmc.fabric.mixin.renderer.client;
|
||||
package net.fabricmc.fabric.mixin.renderer.client.debughud;
|
||||
|
||||
import java.util.List;
|
||||
|
|
@ -1,9 +1,9 @@
|
|||
{
|
||||
"required": false,
|
||||
"package": "net.fabricmc.fabric.mixin.renderer",
|
||||
"package": "net.fabricmc.fabric.mixin.renderer.client.debughud",
|
||||
"compatibilityLevel": "JAVA_16",
|
||||
"client": [
|
||||
"client.MixinDebugHud"
|
||||
"MixinDebugHud"
|
||||
],
|
||||
"injectors": {
|
||||
"defaultRequire": 1
|
||||
|
|
|
@ -4,6 +4,8 @@
|
|||
"compatibilityLevel": "JAVA_16",
|
||||
"client": [
|
||||
"client.MixinBakedModel",
|
||||
"client.MixinMultipartBakedModel",
|
||||
"client.MixinWeightedBakedModel",
|
||||
"client.MixinSpriteAtlasTexture"
|
||||
],
|
||||
"injectors": {
|
||||
|
|
|
@ -27,13 +27,19 @@ import net.minecraft.entity.player.PlayerEntity;
|
|||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.ActionResult;
|
||||
import net.minecraft.util.Hand;
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.hit.BlockHitResult;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.object.builder.v1.block.FabricBlockSettings;
|
||||
|
||||
public final class FrameBlock extends Block implements BlockEntityProvider {
|
||||
public FrameBlock(Settings settings) {
|
||||
super(settings);
|
||||
public final Identifier id;
|
||||
|
||||
public FrameBlock(Identifier id) {
|
||||
super(FabricBlockSettings.copyOf(Blocks.IRON_BLOCK).nonOpaque());
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -22,8 +22,8 @@ import net.minecraft.block.Block;
|
|||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.block.entity.BlockEntity;
|
||||
import net.minecraft.nbt.NbtCompound;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
|
||||
import net.fabricmc.fabric.api.block.entity.BlockEntityClientSerializable;
|
||||
|
@ -84,7 +84,7 @@ public final class FrameBlockEntity extends BlockEntity implements RenderAttachm
|
|||
|
||||
@Override
|
||||
public void fromClientTag(NbtCompound tag) {
|
||||
System.out.println("Recieved sync packet");
|
||||
System.out.println("Received sync packet");
|
||||
|
||||
if (tag.contains("block", NbtType.STRING)) {
|
||||
this.block = Registry.BLOCK.get(new Identifier(tag.getString("block")));
|
||||
|
|
|
@ -16,14 +16,14 @@
|
|||
|
||||
package net.fabricmc.fabric.test.renderer.simple;
|
||||
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.block.Blocks;
|
||||
import net.minecraft.block.entity.BlockEntityType;
|
||||
import net.minecraft.item.BlockItem;
|
||||
import net.minecraft.item.Item;
|
||||
import net.minecraft.item.ItemGroup;
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
|
||||
import net.fabricmc.api.ModInitializer;
|
||||
import net.fabricmc.fabric.api.object.builder.v1.block.FabricBlockSettings;
|
||||
import net.fabricmc.fabric.api.object.builder.v1.block.entity.FabricBlockEntityTypeBuilder;
|
||||
|
||||
/**
|
||||
|
@ -34,12 +34,24 @@ import net.fabricmc.fabric.api.object.builder.v1.block.entity.FabricBlockEntityT
|
|||
* <p>There are no fancy shaders or glow that is provided by this renderer test.
|
||||
*/
|
||||
public final class RendererTest implements ModInitializer {
|
||||
public static final Block FRAME = new FrameBlock(FabricBlockSettings.copyOf(Blocks.IRON_BLOCK).nonOpaque());
|
||||
public static final BlockEntityType<FrameBlockEntity> FRAME_BLOCK_ENTITY = FabricBlockEntityTypeBuilder.create(FrameBlockEntity::new, FRAME).build(null);
|
||||
public static final FrameBlock[] FRAMES = new FrameBlock[] {
|
||||
new FrameBlock(id("frame")),
|
||||
new FrameBlock(id("frame_multipart")),
|
||||
new FrameBlock(id("frame_weighted")),
|
||||
};
|
||||
public static final BlockEntityType<FrameBlockEntity> FRAME_BLOCK_ENTITY = FabricBlockEntityTypeBuilder.create(FrameBlockEntity::new, FRAMES).build(null);
|
||||
|
||||
@Override
|
||||
public void onInitialize() {
|
||||
Registry.register(Registry.BLOCK, new Identifier("fabric-renderer-api-v1-testmod", "frame"), FRAME);
|
||||
Registry.register(Registry.BLOCK_ENTITY_TYPE, new Identifier("fabric-renderer-api-v1-testmod", "frame"), FRAME_BLOCK_ENTITY);
|
||||
for (FrameBlock frameBlock : FRAMES) {
|
||||
Registry.register(Registry.BLOCK, frameBlock.id, frameBlock);
|
||||
Registry.register(Registry.ITEM, frameBlock.id, new BlockItem(frameBlock, new Item.Settings().group(ItemGroup.MISC)));
|
||||
}
|
||||
|
||||
Registry.register(Registry.BLOCK_ENTITY_TYPE, id("frame"), FRAME_BLOCK_ENTITY);
|
||||
}
|
||||
|
||||
public static Identifier id(String path) {
|
||||
return new Identifier("fabric-renderer-api-v1-testmod", path);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -22,7 +22,6 @@ import net.minecraft.client.render.model.UnbakedModel;
|
|||
import net.minecraft.util.Identifier;
|
||||
|
||||
import net.fabricmc.fabric.api.client.model.ModelProviderContext;
|
||||
import net.fabricmc.fabric.api.client.model.ModelProviderException;
|
||||
import net.fabricmc.fabric.api.client.model.ModelResourceProvider;
|
||||
|
||||
/**
|
||||
|
@ -33,7 +32,7 @@ final class FrameModelResourceProvider implements ModelResourceProvider {
|
|||
|
||||
@Nullable
|
||||
@Override
|
||||
public UnbakedModel loadModelResource(Identifier resourceId, ModelProviderContext context) throws ModelProviderException {
|
||||
public UnbakedModel loadModelResource(Identifier resourceId, ModelProviderContext context) {
|
||||
if (resourceId.equals(FRAME_MODEL_ID)) {
|
||||
return new FrameUnbakedModel();
|
||||
}
|
||||
|
|
|
@ -21,12 +21,16 @@ import net.minecraft.client.render.RenderLayer;
|
|||
import net.fabricmc.api.ClientModInitializer;
|
||||
import net.fabricmc.fabric.api.blockrenderlayer.v1.BlockRenderLayerMap;
|
||||
import net.fabricmc.fabric.api.client.model.ModelLoadingRegistry;
|
||||
import net.fabricmc.fabric.test.renderer.simple.FrameBlock;
|
||||
import net.fabricmc.fabric.test.renderer.simple.RendererTest;
|
||||
|
||||
public final class RendererClientTest implements ClientModInitializer {
|
||||
@Override
|
||||
public void onInitializeClient() {
|
||||
ModelLoadingRegistry.INSTANCE.registerResourceProvider(manager -> new FrameModelResourceProvider());
|
||||
BlockRenderLayerMap.INSTANCE.putBlock(RendererTest.FRAME, RenderLayer.getCutoutMipped());
|
||||
|
||||
for (FrameBlock frameBlock : RendererTest.FRAMES) {
|
||||
BlockRenderLayerMap.INSTANCE.putBlock(frameBlock, RenderLayer.getCutoutMipped());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"__comment": "We test that MultipartBakedModel works correctly.",
|
||||
"multipart": [
|
||||
{
|
||||
"apply": {
|
||||
"model": "fabric-renderer-api-v1-testmod:block/frame"
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,13 @@
|
|||
{
|
||||
"__comment": "We test that WeightedBakedModel works correctly, hence the two variants.",
|
||||
"variants": {
|
||||
"": [
|
||||
{
|
||||
"model": "fabric-renderer-api-v1-testmod:block/frame"
|
||||
},
|
||||
{
|
||||
"model": "fabric-renderer-api-v1-testmod:block/frame"
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue