[1.19.3] Implement custom SignTypes ()

* 1.19.3 custom sign types

Co-authored-by: AlphaMode <26313415+alphamode@users.noreply.github.com>

* fix mixin name

Co-authored-by: AlphaMode <26313415+alphamode@users.noreply.github.com>
(cherry picked from commit eb2a3ba986)
This commit is contained in:
Mark 2023-01-20 17:56:36 +00:00 committed by modmuss50
parent d471b08bab
commit 81af046eba
25 changed files with 432 additions and 2 deletions
fabric-object-builder-api-v1/src
fabric-rendering-v1

View file

@ -0,0 +1,46 @@
/*
* 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.object.builder.client;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
import net.minecraft.client.render.entity.model.EntityModelLayer;
import net.minecraft.client.render.entity.model.EntityModelLayers;
import net.minecraft.util.Identifier;
import net.minecraft.util.SignType;
@Mixin(EntityModelLayers.class)
public class EntityModelLayersMixin {
@Inject(method = "createSign", at = @At("HEAD"), cancellable = true)
private static void createSign(SignType type, CallbackInfoReturnable<EntityModelLayer> cir) {
if (type.getName().indexOf(Identifier.NAMESPACE_SEPARATOR) != -1) {
Identifier identifier = new Identifier(type.getName());
cir.setReturnValue(new EntityModelLayer(new Identifier(identifier.getNamespace(), "sign/" + identifier.getPath()), "main"));
}
}
@Inject(method = "createHangingSign", at = @At("HEAD"), cancellable = true)
private static void createHangingSign(SignType type, CallbackInfoReturnable<EntityModelLayer> cir) {
if (type.getName().indexOf(Identifier.NAMESPACE_SEPARATOR) != -1) {
Identifier identifier = new Identifier(type.getName());
cir.setReturnValue(new EntityModelLayer(new Identifier(identifier.getNamespace(), "hanging_sign/" + identifier.getPath()), "main"));
}
}
}

View file

@ -0,0 +1,43 @@
/*
* 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.object.builder.client;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.ModifyArg;
import net.minecraft.block.entity.SignBlockEntity;
import net.minecraft.client.gui.screen.ingame.AbstractSignEditScreen;
import net.minecraft.client.gui.screen.ingame.HangingSignEditScreen;
import net.minecraft.util.Identifier;
@Mixin(HangingSignEditScreen.class)
public abstract class HangingSignEditScreenMixin extends AbstractSignEditScreen {
private HangingSignEditScreenMixin(SignBlockEntity blockEntity, boolean filtered) {
super(blockEntity, filtered);
}
@ModifyArg(method = "<init>", at = @At(value = "INVOKE", target = "Lnet/minecraft/util/Identifier;<init>(Ljava/lang/String;)V"))
private String init(String id) {
if (signType.getName().indexOf(Identifier.NAMESPACE_SEPARATOR) != -1) {
Identifier identifier = new Identifier(signType.getName());
return identifier.getNamespace() + ":textures/gui/hanging_signs/" + identifier.getPath() + ".png";
}
return id;
}
}

View file

@ -0,0 +1,52 @@
/*
* 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.object.builder.client;
import org.spongepowered.asm.mixin.Final;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
import net.minecraft.client.render.TexturedRenderLayers;
import net.minecraft.client.util.SpriteIdentifier;
import net.minecraft.util.Identifier;
import net.minecraft.util.SignType;
@Mixin(TexturedRenderLayers.class)
public class TexturedRenderLayersMixin {
@Shadow
@Final
public static Identifier SIGNS_ATLAS_TEXTURE;
@Inject(method = "createSignTextureId", at = @At("HEAD"), cancellable = true)
private static void modifyTextureId(SignType type, CallbackInfoReturnable<SpriteIdentifier> cir) {
if (type.getName().indexOf(Identifier.NAMESPACE_SEPARATOR) != -1) {
Identifier identifier = new Identifier(type.getName());
cir.setReturnValue(new SpriteIdentifier(SIGNS_ATLAS_TEXTURE, new Identifier(identifier.getNamespace(), "entity/signs/" + identifier.getPath())));
}
}
@Inject(method = "createHangingSignTextureId", at = @At("HEAD"), cancellable = true)
private static void modifyHangingTextureId(SignType type, CallbackInfoReturnable<SpriteIdentifier> cir) {
if (type.getName().indexOf(Identifier.NAMESPACE_SEPARATOR) != -1) {
Identifier identifier = new Identifier(type.getName());
cir.setReturnValue(new SpriteIdentifier(SIGNS_ATLAS_TEXTURE, new Identifier(identifier.getNamespace(), "entity/signs/hanging/" + identifier.getPath())));
}
}
}

View file

@ -3,8 +3,11 @@
"package": "net.fabricmc.fabric.mixin.object.builder.client",
"compatibilityLevel": "JAVA_16",
"client": [
"EntityModelLayersMixin",
"HangingSignEditScreenMixin",
"ModelPredicateProviderRegistryAccessor",
"ModelPredicateProviderRegistrySpecificAccessor"
"ModelPredicateProviderRegistrySpecificAccessor",
"TexturedRenderLayersMixin"
],
"injectors": {
"defaultRequire": 1

View file

@ -0,0 +1,42 @@
/*
* 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.object.builder.v1.sign;
import net.minecraft.util.Identifier;
import net.minecraft.util.SignType;
/**
* This class allows registering {@link SignType}s.
*
* <p>A {@link SignType} is used to tell the game what texture a sign should use.
*
* <p>These textures are stored under {@code namespace/textures/entity/signs/}.
*/
public final class SignTypeRegistry {
private SignTypeRegistry() {
}
/**
* Creates and registers a {@link SignType}.
*
* @param id the id of this {@link SignType}
* @return a new {@link SignType}.
*/
public static SignType registerSignType(Identifier id) {
return SignType.register(new SignType(id.toString()));
}
}

View file

@ -11,3 +11,6 @@ accessible method net/minecraft/entity/SpawnRestriction register (Lnet/minecraft
accessible field net/minecraft/village/VillagerType BIOME_TO_TYPE Ljava/util/Map;
accessible method net/minecraft/village/VillagerType <init> (Ljava/lang/String;)V
accessible method net/minecraft/util/SignType <init> (Ljava/lang/String;)V
accessible method net/minecraft/util/SignType register (Lnet/minecraft/util/SignType;)Lnet/minecraft/util/SignType;

View file

@ -0,0 +1,107 @@
/*
* 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.test.object.builder;
import net.minecraft.block.BlockState;
import net.minecraft.block.Blocks;
import net.minecraft.block.HangingSignBlock;
import net.minecraft.block.SignBlock;
import net.minecraft.block.WallHangingSignBlock;
import net.minecraft.block.WallSignBlock;
import net.minecraft.block.entity.BlockEntityType;
import net.minecraft.block.entity.HangingSignBlockEntity;
import net.minecraft.block.entity.SignBlockEntity;
import net.minecraft.item.HangingSignItem;
import net.minecraft.item.Item;
import net.minecraft.item.SignItem;
import net.minecraft.registry.Registries;
import net.minecraft.registry.Registry;
import net.minecraft.util.SignType;
import net.minecraft.util.math.BlockPos;
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;
import net.fabricmc.fabric.api.object.builder.v1.sign.SignTypeRegistry;
public class TealSignTest implements ModInitializer {
public static final SignType TEAL_TYPE = SignTypeRegistry.registerSignType(ObjectBuilderTestConstants.id("teal"));
public static final SignBlock TEAL_SIGN = new SignBlock(FabricBlockSettings.copy(Blocks.OAK_SIGN), TEAL_TYPE) {
@Override
public TealSign createBlockEntity(BlockPos pos, BlockState state) {
return new TealSign(pos, state);
}
};
public static final WallSignBlock TEAL_WALL_SIGN = new WallSignBlock(FabricBlockSettings.copy(Blocks.OAK_SIGN), TEAL_TYPE) {
@Override
public TealSign createBlockEntity(BlockPos pos, BlockState state) {
return new TealSign(pos, state);
}
};
public static final HangingSignBlock TEAL_HANGING_SIGN = new HangingSignBlock(FabricBlockSettings.copy(Blocks.OAK_HANGING_SIGN), TEAL_TYPE) {
@Override
public TealHangingSign createBlockEntity(BlockPos pos, BlockState state) {
return new TealHangingSign(pos, state);
}
};
public static final WallHangingSignBlock TEAL_WALL_HANGING_SIGN = new WallHangingSignBlock(FabricBlockSettings.copy(Blocks.OAK_HANGING_SIGN), TEAL_TYPE) {
@Override
public TealHangingSign createBlockEntity(BlockPos pos, BlockState state) {
return new TealHangingSign(pos, state);
}
};
public static final SignItem TEAL_SIGN_ITEM = new SignItem(new Item.Settings(), TEAL_SIGN, TEAL_WALL_SIGN);
public static final HangingSignItem TEAL_HANGING_SIGN_ITEM = new HangingSignItem(TEAL_HANGING_SIGN, TEAL_WALL_HANGING_SIGN, new Item.Settings());
public static final BlockEntityType<TealSign> TEST_SIGN_BLOCK_ENTITY = FabricBlockEntityTypeBuilder.create(TealSign::new, TEAL_SIGN, TEAL_WALL_SIGN).build();
public static final BlockEntityType<TealHangingSign> TEST_HANGING_SIGN_BLOCK_ENTITY = FabricBlockEntityTypeBuilder.create(TealHangingSign::new, TEAL_HANGING_SIGN, TEAL_WALL_HANGING_SIGN).build();
@Override
public void onInitialize() {
Registry.register(Registries.BLOCK, ObjectBuilderTestConstants.id("teal_sign"), TEAL_SIGN);
Registry.register(Registries.BLOCK, ObjectBuilderTestConstants.id("teal_wall_sign"), TEAL_WALL_SIGN);
Registry.register(Registries.BLOCK, ObjectBuilderTestConstants.id("teal_hanging_sign"), TEAL_HANGING_SIGN);
Registry.register(Registries.BLOCK, ObjectBuilderTestConstants.id("teal_wall_hanging_sign"), TEAL_WALL_HANGING_SIGN);
Registry.register(Registries.ITEM, ObjectBuilderTestConstants.id("teal_sign"), TEAL_SIGN_ITEM);
Registry.register(Registries.ITEM, ObjectBuilderTestConstants.id("teal_hanging_sign"), TEAL_HANGING_SIGN_ITEM);
Registry.register(Registries.BLOCK_ENTITY_TYPE, ObjectBuilderTestConstants.id("teal_sign"), TEST_SIGN_BLOCK_ENTITY);
Registry.register(Registries.BLOCK_ENTITY_TYPE, ObjectBuilderTestConstants.id("teal_hanging_sign"), TEST_HANGING_SIGN_BLOCK_ENTITY);
}
public static class TealSign extends SignBlockEntity {
public TealSign(BlockPos pos, BlockState state) {
super(pos, state);
}
@Override
public BlockEntityType<?> getType() {
return TEST_SIGN_BLOCK_ENTITY;
}
}
public static class TealHangingSign extends HangingSignBlockEntity {
public TealHangingSign(BlockPos pos, BlockState state) {
super(pos, state);
}
@Override
public BlockEntityType<?> getType() {
return TEST_HANGING_SIGN_BLOCK_ENTITY;
}
}
}

View file

@ -0,0 +1,32 @@
/*
* 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.test.object.builder.client;
import net.minecraft.client.render.block.entity.HangingSignBlockEntityRenderer;
import net.minecraft.client.render.block.entity.SignBlockEntityRenderer;
import net.fabricmc.api.ClientModInitializer;
import net.fabricmc.fabric.test.object.builder.TealSignTest;
import net.fabricmc.fabric.test.object.builder.mixin.BlockEntityRendererFactoriesAccessor;
public class TealSignClientTest implements ClientModInitializer {
@Override
public void onInitializeClient() {
BlockEntityRendererFactoriesAccessor.callRegister(TealSignTest.TEST_SIGN_BLOCK_ENTITY, SignBlockEntityRenderer::new);
BlockEntityRendererFactoriesAccessor.callRegister(TealSignTest.TEST_HANGING_SIGN_BLOCK_ENTITY, HangingSignBlockEntityRenderer::new);
}
}

View file

@ -0,0 +1,33 @@
/*
* 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.test.object.builder.mixin;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.gen.Invoker;
import net.minecraft.block.entity.BlockEntity;
import net.minecraft.block.entity.BlockEntityType;
import net.minecraft.client.render.block.entity.BlockEntityRendererFactories;
import net.minecraft.client.render.block.entity.BlockEntityRendererFactory;
@Mixin(BlockEntityRendererFactories.class)
public interface BlockEntityRendererFactoriesAccessor {
@Invoker
static <T extends BlockEntity> void callRegister(BlockEntityType<? extends T> type, BlockEntityRendererFactory<T> factory) {
throw new UnsupportedOperationException();
}
}

View file

@ -0,0 +1,7 @@
{
"variants": {
"": {
"model": "fabric-rendering-v1-testmod:block/teal_hanging_sign"
}
}
}

View file

@ -0,0 +1,7 @@
{
"variants": {
"": {
"model": "fabric-rendering-v1-testmod:block/teal_sign"
}
}
}

View file

@ -0,0 +1,7 @@
{
"variants": {
"": {
"model": "fabric-rendering-v1-testmod:block/teal_hanging_sign"
}
}
}

View file

@ -0,0 +1,7 @@
{
"variants": {
"": {
"model": "fabric-rendering-v1-testmod:block/teal_sign"
}
}
}

View file

@ -3,5 +3,7 @@
"block.fabric-object-builder-api-v1-testmod.first_multi_betrayal_block": "First Multi Betrayal Block",
"block.fabric-object-builder-api-v1-testmod.initial_betrayal_block": "Initial Betrayal Block",
"block.fabric-object-builder-api-v1-testmod.second_multi_betrayal_block": "Second Multi Betrayal Block",
"block.fabric-object-builder-api-v1-testmod.teal_sign": "Teal Sign",
"block.fabric-object-builder-api-v1-testmod.teal_hanging_sign": "Teal Hanging Sign",
"text.fabric-object-builder-api-v1-testmod.block_entity_type_success": "Betrayal block at %s has correct block entity type: %s"
}

View file

@ -0,0 +1,5 @@
{
"textures": {
"particle": "fabric-object-builder-api-v1-testmod:entity/signs/teal"
}
}

View file

@ -0,0 +1,6 @@
{
"parent": "minecraft:item/generated",
"textures": {
"layer0": "fabric-object-builder-api-v1-testmod:item/teal_hanging_sign"
}
}

View file

@ -0,0 +1,6 @@
{
"parent": "minecraft:item/generated",
"textures": {
"layer0": "fabric-object-builder-api-v1-testmod:item/teal_sign"
}
}

View file

@ -0,0 +1,11 @@
{
"required": true,
"package": "net.fabricmc.fabric.test.object.builder.mixin",
"compatibilityLevel": "JAVA_17",
"client": [
"BlockEntityRendererFactoriesAccessor"
],
"injectors": {
"defaultRequire": 1
}
}

View file

@ -20,12 +20,19 @@
"fabric-object-builder-api-v1": "*"
},
"description": "Test mod for fabric object builder API v1.",
"mixins": [
"fabric-object-builder-api-v1-testmod.mixins.json"
],
"entrypoints": {
"main": [
"net.fabricmc.fabric.test.object.builder.BlockEntityTypeBuilderTest",
"net.fabricmc.fabric.test.object.builder.CriterionRegistryTest::init",
"net.fabricmc.fabric.test.object.builder.VillagerTypeTest1",
"net.fabricmc.fabric.test.object.builder.VillagerTypeTest2"
"net.fabricmc.fabric.test.object.builder.VillagerTypeTest2",
"net.fabricmc.fabric.test.object.builder.TealSignTest"
],
"client": [
"net.fabricmc.fabric.test.object.builder.client.TealSignClientTest"
],
"fabric-gametest": [
"net.fabricmc.fabric.test.object.builder.ObjectBuilderGameTest"

View file

@ -4,3 +4,7 @@ version = getSubprojectVersion(project)
moduleDependencies(project, [
'fabric-api-base'
])
testDependencies(project, [
':fabric-object-builder-api-v1'
])