mirror of
https://github.com/MineLittlePony/MineLittlePony.git
synced 2025-02-13 08:14:23 +01:00
Merge branch '1.21.3' into 1.21.4
# Conflicts: # src/main/java/com/minelittlepony/client/render/entity/feature/ArmourFeature.java
This commit is contained in:
commit
6b7b33958b
6 changed files with 109 additions and 8 deletions
|
@ -1 +1 @@
|
||||||
Subproject commit 1ae97d064e7579d94a93f2784473dc7ce0e1e670
|
Subproject commit 913c35681b09cfbab0bf5def678db3407f5834bb
|
|
@ -77,6 +77,15 @@ public class PonyConfig extends Config {
|
||||||
.addComment("Disables certain easter eggs and secrets (party pooper)")
|
.addComment("Disables certain easter eggs and secrets (party pooper)")
|
||||||
.addComment("Turning this off may help with compatibility in some cases");
|
.addComment("Turning this off may help with compatibility in some cases");
|
||||||
|
|
||||||
|
public final Setting<Boolean> enableFabricModelsApiSupport = value("settings", "enableFabricModelsApiSupport", false)
|
||||||
|
.addComment("Enables rendering of modded armour registered via the fabric api")
|
||||||
|
.addComment("Note that since any armour registered in this way is designed to work for the human model, pieces may not fit exactly.")
|
||||||
|
.addComment("i.e. Anything that goes on the plyer's backs needs to be rotated by the mod developer when rendered on a pony")
|
||||||
|
.addComment("Developers: To know if you're being rendered on a pony model, check the renderstate or model class with")
|
||||||
|
.addComment(" state instanceof com.minelittlepony.api.model.PonyModel$AttributedHolder or model instanceof com.minelittlepony.api.model.PonyModel")
|
||||||
|
.addComment(" Note that the matrix stack your receieve is pre-transformed for the body part your model is attached to, so if you intend to call model.transform(state, part, matrices)")
|
||||||
|
.addComment(" with a different part (ie BACK) you must pop the stack to revert to the previous first.");
|
||||||
|
|
||||||
public final Setting<VisibilityMode> horseButton = value("horseButton", VisibilityMode.AUTO)
|
public final Setting<VisibilityMode> horseButton = value("horseButton", VisibilityMode.AUTO)
|
||||||
.addComment("Whether to show the mine little pony settings button on the main menu")
|
.addComment("Whether to show the mine little pony settings button on the main menu")
|
||||||
.addComment("AUTO (default) - only show when HDSkins is not installed")
|
.addComment("AUTO (default) - only show when HDSkins is not installed")
|
||||||
|
|
|
@ -23,7 +23,6 @@ import com.minelittlepony.api.model.Models;
|
||||||
import com.minelittlepony.client.model.AbstractPonyModel;
|
import com.minelittlepony.client.model.AbstractPonyModel;
|
||||||
import com.minelittlepony.client.model.ClientPonyModel;
|
import com.minelittlepony.client.model.ClientPonyModel;
|
||||||
import com.minelittlepony.client.render.entity.state.PonyRenderState;
|
import com.minelittlepony.client.render.entity.state.PonyRenderState;
|
||||||
|
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
|
||||||
public class PonifiedEquipmentRenderer extends EquipmentRenderer {
|
public class PonifiedEquipmentRenderer extends EquipmentRenderer {
|
||||||
|
|
|
@ -1,21 +1,31 @@
|
||||||
package com.minelittlepony.client.render.entity.feature;
|
package com.minelittlepony.client.render.entity.feature;
|
||||||
|
|
||||||
import com.minelittlepony.api.model.Models;
|
import com.minelittlepony.api.config.PonyConfig;
|
||||||
|
import com.minelittlepony.api.model.*;
|
||||||
import com.minelittlepony.client.model.ClientPonyModel;
|
import com.minelittlepony.client.model.ClientPonyModel;
|
||||||
import com.minelittlepony.client.model.armour.*;
|
import com.minelittlepony.client.model.armour.*;
|
||||||
import com.minelittlepony.client.render.PonyRenderContext;
|
import com.minelittlepony.client.render.PonyRenderContext;
|
||||||
import com.minelittlepony.client.render.entity.state.PonyRenderState;
|
import com.minelittlepony.client.render.entity.state.PonyRenderState;
|
||||||
|
import com.minelittlepony.client.util.render.MatrixStackUtil;
|
||||||
|
|
||||||
|
import java.util.*;
|
||||||
|
|
||||||
|
import net.fabricmc.fabric.api.client.rendering.v1.ArmorRenderer;
|
||||||
|
import net.fabricmc.fabric.impl.client.rendering.ArmorRendererRegistryImpl;
|
||||||
import net.minecraft.client.render.*;
|
import net.minecraft.client.render.*;
|
||||||
import net.minecraft.client.render.entity.equipment.EquipmentModel;
|
import net.minecraft.client.render.entity.equipment.EquipmentModel;
|
||||||
import net.minecraft.client.render.entity.equipment.EquipmentModelLoader;
|
import net.minecraft.client.render.entity.equipment.EquipmentModelLoader;
|
||||||
|
import net.minecraft.client.render.entity.model.BipedEntityModel;
|
||||||
import net.minecraft.client.util.math.MatrixStack;
|
import net.minecraft.client.util.math.MatrixStack;
|
||||||
import net.minecraft.component.DataComponentTypes;
|
import net.minecraft.component.DataComponentTypes;
|
||||||
import net.minecraft.component.type.EquippableComponent;
|
import net.minecraft.component.type.EquippableComponent;
|
||||||
import net.minecraft.entity.EquipmentSlot;
|
import net.minecraft.entity.EquipmentSlot;
|
||||||
import net.minecraft.entity.LivingEntity;
|
import net.minecraft.entity.LivingEntity;
|
||||||
import net.minecraft.item.*;
|
import net.minecraft.item.*;
|
||||||
|
import net.minecraft.util.Unit;
|
||||||
|
|
||||||
|
import org.apache.logging.log4j.LogManager;
|
||||||
|
import org.apache.logging.log4j.Logger;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
|
||||||
public class ArmourFeature<
|
public class ArmourFeature<
|
||||||
|
@ -23,6 +33,9 @@ public class ArmourFeature<
|
||||||
S extends PonyRenderState,
|
S extends PonyRenderState,
|
||||||
M extends ClientPonyModel<S>
|
M extends ClientPonyModel<S>
|
||||||
> extends AbstractPonyFeature<S, M> {
|
> extends AbstractPonyFeature<S, M> {
|
||||||
|
private static final Logger LOGGER = LogManager.getLogger("PonifiedEquipmentRenderer");
|
||||||
|
|
||||||
|
private static boolean FABRIC_API_FAILURE;
|
||||||
|
|
||||||
private final PonifiedEquipmentRenderer equipmentRenderer;
|
private final PonifiedEquipmentRenderer equipmentRenderer;
|
||||||
|
|
||||||
|
@ -58,17 +71,77 @@ public class ArmourFeature<
|
||||||
ArmourRendererPlugin plugin = ArmourRendererPlugin.INSTANCE.get();
|
ArmourRendererPlugin plugin = ArmourRendererPlugin.INSTANCE.get();
|
||||||
|
|
||||||
for (ItemStack stack : plugin.getArmorStacks(entity, armorSlot, layerType, ArmourRendererPlugin.ArmourType.ARMOUR)) {
|
for (ItemStack stack : plugin.getArmorStacks(entity, armorSlot, layerType, ArmourRendererPlugin.ArmourType.ARMOUR)) {
|
||||||
EquippableComponent equippableComponent = stack.get(DataComponentTypes.EQUIPPABLE);
|
render(armorSlot, layerType, entity, models, stack, matrices, vertices, light, equipmentRenderer);
|
||||||
|
|
||||||
if (hasModel(equippableComponent, armorSlot)) {
|
|
||||||
equipmentRenderer.render(armorSlot, layerType, equippableComponent.assetId().orElseThrow(), entity, models, stack, matrices, vertices, light);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
plugin.onArmourRendered(entity, matrices, vertices, armorSlot, layerType, ArmourRendererPlugin.ArmourType.ARMOUR);
|
plugin.onArmourRendered(entity, matrices, vertices, armorSlot, layerType, ArmourRendererPlugin.ArmourType.ARMOUR);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static <S extends PonyRenderState, V extends ClientPonyModel<S>> void render(
|
||||||
|
EquipmentSlot slot,
|
||||||
|
EquipmentModel.LayerType layerType,
|
||||||
|
S entity,
|
||||||
|
Models<V> models,
|
||||||
|
ItemStack stack,
|
||||||
|
MatrixStack matrices,
|
||||||
|
VertexConsumerProvider vertices,
|
||||||
|
int light, PonifiedEquipmentRenderer equipmentRenderer
|
||||||
|
) {
|
||||||
|
if (!FABRIC_API_FAILURE && PonyConfig.getInstance().enableFabricModelsApiSupport.get()) {
|
||||||
|
try {
|
||||||
|
if (FabricArmorRendererInvoker.renderArmor(stack, models, matrices, vertices, light, entity, slot, layerType)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} catch (Throwable t) {
|
||||||
|
LOGGER.error("Failure calling fabric armor rendering api", t);
|
||||||
|
FABRIC_API_FAILURE = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
EquippableComponent equippableComponent = stack.get(DataComponentTypes.EQUIPPABLE);
|
||||||
|
if (hasModel(equippableComponent, slot)) {
|
||||||
|
equipmentRenderer.render(slot, layerType, equippableComponent.assetId().orElseThrow(), entity, models, stack, matrices, vertices, light, null);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private static boolean hasModel(@Nullable EquippableComponent component, EquipmentSlot slot) {
|
private static boolean hasModel(@Nullable EquippableComponent component, EquipmentSlot slot) {
|
||||||
return component != null && component.assetId().isPresent() && component.slot() == slot;
|
return component != null && component.assetId().isPresent() && component.slot() == slot;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static final class FabricArmorRendererInvoker {
|
||||||
|
private static final Map<ArmorRenderer, Unit> FAILING_RENDERERS = new WeakHashMap<>();
|
||||||
|
|
||||||
|
@SuppressWarnings({"rawtypes", "unchecked"})
|
||||||
|
private static <S extends PonyRenderState, V extends ClientPonyModel<S>> boolean renderArmor(
|
||||||
|
ItemStack stack,
|
||||||
|
Models<V> models, MatrixStack matrices,
|
||||||
|
VertexConsumerProvider vertices, int light, S entity,
|
||||||
|
EquipmentSlot armorSlot, EquipmentModel.LayerType layerType) {
|
||||||
|
ArmorRenderer renderer = ArmorRendererRegistryImpl.get(stack.getItem());
|
||||||
|
|
||||||
|
if (renderer != null && !FAILING_RENDERERS.containsKey(renderer)) {
|
||||||
|
MatrixStack isolation = MatrixStackUtil.pushIsolation(matrices);
|
||||||
|
try {
|
||||||
|
isolation.push();
|
||||||
|
models.body().transform(entity, getBodyPart(armorSlot), isolation);
|
||||||
|
renderer.render(isolation, vertices, stack, entity, armorSlot, light, (BipedEntityModel)models.body());
|
||||||
|
isolation.pop();
|
||||||
|
} catch (Throwable t) {
|
||||||
|
LOGGER.error("Exception occured whilst rendering custom armor via fabric api. Renderer {} has been disabled", renderer, t);
|
||||||
|
FAILING_RENDERERS.put(renderer, Unit.INSTANCE);
|
||||||
|
} finally {
|
||||||
|
MatrixStackUtil.popIsolation();
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static BodyPart getBodyPart(EquipmentSlot slot) {
|
||||||
|
return switch (slot) {
|
||||||
|
case HEAD -> BodyPart.HEAD;
|
||||||
|
case CHEST, BODY -> BodyPart.BODY;
|
||||||
|
case LEGS, FEET, MAINHAND, OFFHAND -> BodyPart.LEGS;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,19 @@
|
||||||
|
package com.minelittlepony.client.util.render;
|
||||||
|
|
||||||
|
import net.minecraft.client.util.math.MatrixStack;
|
||||||
|
|
||||||
|
public class MatrixStackUtil {
|
||||||
|
static final MatrixStack ISOLATION_STACK = new MatrixStack();
|
||||||
|
|
||||||
|
public static MatrixStack pushIsolation(MatrixStack matrices) {
|
||||||
|
ISOLATION_STACK.peek().getNormalMatrix().set(matrices.peek().getNormalMatrix());
|
||||||
|
ISOLATION_STACK.peek().getPositionMatrix().set(matrices.peek().getPositionMatrix());
|
||||||
|
return ISOLATION_STACK;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void popIsolation() {
|
||||||
|
while (!ISOLATION_STACK.isEmpty()) {
|
||||||
|
ISOLATION_STACK.pop();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -14,6 +14,7 @@
|
||||||
"minelp.options.skins.hdskins.open": "Open HD Skins",
|
"minelp.options.skins.hdskins.open": "Open HD Skins",
|
||||||
"minelp.options.skins.hdskins.disabled": "HD Skins is not installed\n\nThe HD Skins mod is required to upload skins from in-game and to use custom skin servers.\n\nIf you cannot use that you will have to go to www.minecraft.net to upload your skin there.",
|
"minelp.options.skins.hdskins.disabled": "HD Skins is not installed\n\nThe HD Skins mod is required to upload skins from in-game and to use custom skin servers.\n\nIf you cannot use that you will have to go to www.minecraft.net to upload your skin there.",
|
||||||
"minelp.options.snuzzles": "Show Snuzzles",
|
"minelp.options.snuzzles": "Show Snuzzles",
|
||||||
|
"minelp.options.enablefabricmodelsapisupport": "(Experimental) Show Modded Armor",
|
||||||
"minelp.options.fillycam": "Filly Cam",
|
"minelp.options.fillycam": "Filly Cam",
|
||||||
"minelp.options.showscale": "Show-accurate scaling",
|
"minelp.options.showscale": "Show-accurate scaling",
|
||||||
"minelp.options.fpsmagic": "Magic in first-person",
|
"minelp.options.fpsmagic": "Magic in first-person",
|
||||||
|
|
Loading…
Reference in a new issue