Rewrite armour AGAIN

This commit is contained in:
Sollace 2018-08-16 21:31:24 +02:00
parent 902571198b
commit 4bea2e77a3
7 changed files with 173 additions and 115 deletions

View file

@ -1,7 +1,10 @@
package com.minelittlepony.model.armour; package com.minelittlepony.model.armour;
import net.minecraft.inventory.EntityEquipmentSlot;
public interface IEquestrianArmor { public interface IEquestrianArmor {
ModelPonyArmor getArmorForSlot(EntityEquipmentSlot slot); ModelPonyArmor getArmorForLayer(ArmorLayer layer);
enum ArmorLayer {
INNER,
OUTER
}
} }

View file

@ -3,19 +3,17 @@ package com.minelittlepony.model.armour;
import net.minecraft.client.model.ModelBiped; import net.minecraft.client.model.ModelBiped;
import net.minecraft.entity.Entity; import net.minecraft.entity.Entity;
import static com.minelittlepony.model.PonyModelConstants.*;
import com.minelittlepony.model.AbstractPonyModel; import com.minelittlepony.model.AbstractPonyModel;
import com.minelittlepony.model.capabilities.IModel; import com.minelittlepony.model.capabilities.IModel;
import com.minelittlepony.model.capabilities.IModelArmor; import com.minelittlepony.model.capabilities.IModelArmor;
import com.minelittlepony.render.PonyRenderer; import com.minelittlepony.render.PonyRenderer;
import static com.minelittlepony.model.PonyModelConstants.*;
public class ModelPonyArmor extends AbstractPonyModel implements IModelArmor { public class ModelPonyArmor extends AbstractPonyModel implements IModelArmor {
public PonyRenderer flankGuard; public PonyRenderer flankGuard;
public PonyRenderer saddle;
public ModelPonyArmor() { public ModelPonyArmor() {
super(false); super(false);
textureHeight = 32; textureHeight = 32;
@ -28,27 +26,15 @@ public class ModelPonyArmor extends AbstractPonyModel implements IModelArmor {
flankGuard.rotateAngleX = rotateAngleX; flankGuard.rotateAngleX = rotateAngleX;
flankGuard.rotationPointY = rotationPointY; flankGuard.rotationPointY = rotationPointY;
flankGuard.rotationPointZ = rotationPointZ; flankGuard.rotationPointZ = rotationPointZ;
saddle.rotateAngleX = rotateAngleX;
saddle.rotationPointY = rotationPointY;
saddle.rotationPointZ = rotationPointZ;
} }
@Override @Override
protected void renderBody(Entity entity, float move, float swing, float ticks, float headYaw, float headPitch, float scale) { protected void renderBody(Entity entity, float move, float swing, float ticks, float headYaw, float headPitch, float scale) {
flankGuard.render(scale); flankGuard.render(scale);
saddle.render(scale);
} }
@Override @Override
protected void renderLegs(float scale) { protected void renderLegs(float scale) {
if (!isSneak) {
boolean isLegs = saddle.showModel;
saddle.showModel = true;
saddle.postRender(scale);
saddle.showModel = isLegs;
}
super.renderLegs(scale); super.renderLegs(scale);
} }
@ -71,10 +57,7 @@ public class ModelPonyArmor extends AbstractPonyModel implements IModelArmor {
protected void initBody(float yOffset, float stretch) { protected void initBody(float yOffset, float stretch) {
super.initBody(yOffset, stretch); super.initBody(yOffset, stretch);
flankGuard = new PonyRenderer(this, 0, 0) flankGuard = new PonyRenderer(this, 16, 8)
.around(HEAD_RP_X, HEAD_RP_Y + yOffset, HEAD_RP_Z)
.box(-4, 4, 6, 8, 8, 8, stretch);
saddle = new PonyRenderer(this, 16, 8)
.around(HEAD_RP_X, HEAD_RP_Y + yOffset, HEAD_RP_Z) .around(HEAD_RP_X, HEAD_RP_Y + yOffset, HEAD_RP_Z)
.box(-4, 4, -2, 8, 8, 16, stretch); .box(-4, 4, -2, 8, 8, 16, stretch);
} }
@ -89,34 +72,41 @@ public class ModelPonyArmor extends AbstractPonyModel implements IModelArmor {
} }
@Override @Override
public void setVisible(boolean invisible) { public void setInVisible() {
super.setVisible(invisible); setVisible(false);
flankGuard.showModel = invisible; flankGuard.showModel = false;
saddle.showModel = invisible; bipedHead.showModel = false;
bipedHead.showModel = invisible;
tail.setVisible(false); tail.setVisible(false);
neck.isHidden = true; neck.isHidden = true;
upperTorso.isHidden = true; upperTorso.isHidden = true;
snout.isHidden = true; snout.isHidden = true;
} }
public void showFeet(boolean show) { @Override
bipedRightArm.showModel = show; public void showBoots() {
bipedLeftArm.showModel = show; bipedRightArm.showModel = true;
bipedRightLeg.showModel = show; bipedLeftArm.showModel = true;
bipedLeftLeg.showModel = show; bipedRightLeg.showModel = true;
bipedLeftLeg.showModel = true;
} }
public void showLegs(boolean isPony) { @Override
bipedBody.showModel = true; public void showLeggings() {
showBoots();
} }
public void showSaddle(boolean isPony) { @Override
flankGuard.showModel = !isPony; public void showChestplate() {
saddle.showModel = isPony; flankGuard.showModel = true;
} }
public void showHead(boolean show) { @Override
bipedHead.showModel = show; public void showSaddle() {
flankGuard.showModel = true;
}
@Override
public void showHelmet() {
bipedHead.showModel = true;
} }
} }

View file

@ -3,36 +3,34 @@ package com.minelittlepony.model.armour;
import com.minelittlepony.model.capabilities.IModelWrapper; import com.minelittlepony.model.capabilities.IModelWrapper;
import com.minelittlepony.pony.data.IPonyData; import com.minelittlepony.pony.data.IPonyData;
import net.minecraft.inventory.EntityEquipmentSlot;
public class PonyArmor implements IModelWrapper, IEquestrianArmor { public class PonyArmor implements IModelWrapper, IEquestrianArmor {
public final ModelPonyArmor chestplate; public final ModelPonyArmor outerLayer;
public final ModelPonyArmor leggings; public final ModelPonyArmor innerLayer;
public PonyArmor(ModelPonyArmor chest, ModelPonyArmor body) { public PonyArmor(ModelPonyArmor outer, ModelPonyArmor inner) {
chestplate = chest; outerLayer = outer;
leggings = body; innerLayer = inner;
} }
@Override @Override
public void apply(IPonyData meta) { public void apply(IPonyData meta) {
chestplate.metadata = meta; outerLayer.metadata = meta;
leggings.metadata = meta; innerLayer.metadata = meta;
} }
@Override @Override
public void init() { public void init() {
chestplate.init(0, 1); outerLayer.init(0, 1);
leggings.init(0, 0.5f); innerLayer.init(0, 0.5F);
} }
@Override @Override
public ModelPonyArmor getArmorForSlot(EntityEquipmentSlot slot) { public ModelPonyArmor getArmorForLayer(ArmorLayer layer) {
if (slot == EntityEquipmentSlot.LEGS) { if (layer == ArmorLayer.INNER) {
return leggings; return innerLayer;
} }
return chestplate; return outerLayer;
} }
} }

View file

@ -1,15 +1,90 @@
package com.minelittlepony.model.capabilities; package com.minelittlepony.model.capabilities;
import net.minecraft.client.model.ModelBiped; import net.minecraft.client.model.ModelBiped;
import net.minecraft.inventory.EntityEquipmentSlot;
import com.minelittlepony.model.armour.IEquestrianArmor.ArmorLayer;
public interface IModelArmor extends IModel { public interface IModelArmor extends IModel {
/**
* Called to synchronise this model's legs with that of another.
*
* @param model The other model to mimic
*/
<T extends ModelBiped & IModel> void synchroniseLegs(T model); <T extends ModelBiped & IModel> void synchroniseLegs(T model);
void showFeet(boolean show); /**
* Resets the state of this model to all invisible.
*/
void setInVisible();
void showLegs(boolean isPony); /**
* Prepares an armour model for rendering, first hiding all the pieces and then incrementally showing them as appropriate.
*
* @param slot The armour slot being rendered
* @param layer The layer. INNER/OUTER
*
* @return false to skip this render pass.
*/
default boolean prepareToRender(EntityEquipmentSlot slot, ArmorLayer layer) {
setInVisible();
void showSaddle(boolean isPony); switch (layer) {
case OUTER:
switch (slot) {
case HEAD:
showHelmet();
return true;
case FEET:
showBoots();
return true;
case CHEST:
showSaddle();
return true;
default:
return false;
}
case INNER:
switch (slot) {
case LEGS:
showLeggings();
return true;
case CHEST:
showChestplate();
return true;
default:
return false;
}
}
void showHead(boolean show); return false;
}
/**
* Called to display the model's boots.
*/
void showBoots();
/**
* Called to display the leg part of the model. Legs and boots use the same components just with separated texture files
* so it's reasonable that this would also call showBoots()
*/
void showLeggings();
/**
* Shows the chestplate and saddle.
*
* @param outside true when being called to render the external cloth layer (saddle), false for the main body piece.
*/
void showChestplate();
/**
* Ponies wear saddles. #dealwithit
*/
void showSaddle();
/**
* Used to make the helmet visible
*/
void showHelmet();
} }

View file

@ -4,6 +4,7 @@ import com.google.common.collect.Maps;
import com.minelittlepony.ForgeProxy; import com.minelittlepony.ForgeProxy;
import com.minelittlepony.model.ModelWrapper; import com.minelittlepony.model.ModelWrapper;
import com.minelittlepony.model.armour.IEquestrianArmor; import com.minelittlepony.model.armour.IEquestrianArmor;
import com.minelittlepony.model.armour.IEquestrianArmor.ArmorLayer;
import com.minelittlepony.model.armour.ModelPonyArmor; import com.minelittlepony.model.armour.ModelPonyArmor;
import com.minelittlepony.model.capabilities.IModelArmor; import com.minelittlepony.model.capabilities.IModelArmor;
import com.minelittlepony.util.coordinates.Color; import com.minelittlepony.util.coordinates.Color;
@ -45,33 +46,36 @@ public class LayerPonyArmor<T extends EntityLivingBase> extends AbstractPonyLaye
for (EntityEquipmentSlot i : EntityEquipmentSlot.values()) { for (EntityEquipmentSlot i : EntityEquipmentSlot.values()) {
if (i.getSlotType() == Type.ARMOR) { if (i.getSlotType() == Type.ARMOR) {
renderArmor(entity, move, swing, partialTicks, ticks, headYaw, headPitch, scale, i); renderArmor(entity, move, swing, partialTicks, ticks, headYaw, headPitch, scale, i, ArmorLayer.INNER);
renderArmor(entity, move, swing, partialTicks, ticks, headYaw, headPitch, scale, i, ArmorLayer.OUTER);
} }
} }
} }
private <V extends ModelBiped & IModelArmor> void renderArmor(T entity, float move, float swing, float partialTicks, float ticks, float headYaw, float headPitch, float scale, EntityEquipmentSlot armorSlot) { private <V extends ModelBiped & IModelArmor> void renderArmor(T entity, float move, float swing, float partialTicks, float ticks, float headYaw, float headPitch, float scale, EntityEquipmentSlot armorSlot, ArmorLayer layer) {
ItemStack itemstack = entity.getItemStackFromSlot(armorSlot); ItemStack itemstack = entity.getItemStackFromSlot(armorSlot);
if (!itemstack.isEmpty() && itemstack.getItem() instanceof ItemArmor) { if (!itemstack.isEmpty() && itemstack.getItem() instanceof ItemArmor) {
ItemArmor itemarmor = (ItemArmor) itemstack.getItem(); ItemArmor itemarmor = (ItemArmor) itemstack.getItem();
ModelPonyArmor armour = getArmorModel(entity, itemstack, armorSlot, pony.getArmor().getArmorForSlot(armorSlot)); ModelPonyArmor armour = getArmorModel(entity, itemstack, armorSlot, layer, pony.getArmor().getArmorForLayer(layer));
if (armour.prepareToRender(armorSlot, layer)) {
armour.setModelAttributes(pony.getBody()); armour.setModelAttributes(pony.getBody());
armour.setRotationAngles(move, swing, ticks, headYaw, headPitch, scale, entity); armour.setRotationAngles(move, swing, ticks, headYaw, headPitch, scale, entity);
armour.synchroniseLegs(pony.getBody()); armour.synchroniseLegs(pony.getBody());
Tuple<ResourceLocation, Boolean> armors = getArmorTexture(entity, itemstack, armorSlot, null); Tuple<ResourceLocation, Boolean> armourTexture = getArmorTexture(entity, itemstack, armorSlot, layer, null);
prepareToRender(armour, armorSlot, armors.getSecond());
getRenderer().bindTexture(armors.getFirst()); getRenderer().bindTexture(armourTexture.getFirst());
if (itemarmor.getArmorMaterial() == ArmorMaterial.LEATHER) { if (itemarmor.getArmorMaterial() == ArmorMaterial.LEATHER) {
Color.glColor(itemarmor.getColor(itemstack), 1); Color.glColor(itemarmor.getColor(itemstack), 1);
armour.render(entity, move, swing, ticks, headYaw, headPitch, scale); armour.render(entity, move, swing, ticks, headYaw, headPitch, scale);
armors = getArmorTexture(entity, itemstack, armorSlot, "overlay"); armourTexture = getArmorTexture(entity, itemstack, armorSlot, layer, "overlay");
getRenderer().bindTexture(armors.getFirst()); getRenderer().bindTexture(armourTexture.getFirst());
} }
GlStateManager.color(1, 1, 1, 1); GlStateManager.color(1, 1, 1, 1);
@ -82,8 +86,9 @@ public class LayerPonyArmor<T extends EntityLivingBase> extends AbstractPonyLaye
} }
} }
} }
}
private Tuple<ResourceLocation, Boolean> getArmorTexture(T entity, ItemStack itemstack, EntityEquipmentSlot slot, @Nullable String type) { private Tuple<ResourceLocation, Boolean> getArmorTexture(T entity, ItemStack itemstack, EntityEquipmentSlot slot, ArmorLayer layer, @Nullable String type) {
ItemArmor item = (ItemArmor) itemstack.getItem(); ItemArmor item = (ItemArmor) itemstack.getItem();
String texture = item.getArmorMaterial().getName(); String texture = item.getArmorMaterial().getName();
@ -97,56 +102,41 @@ public class LayerPonyArmor<T extends EntityLivingBase> extends AbstractPonyLaye
type = type == null ? "" : String.format("_%s", type); type = type == null ? "" : String.format("_%s", type);
String ponyRes = String.format("%s:textures/models/armor/%s_layer_%d%s.png", domain, texture, slot == EntityEquipmentSlot.LEGS ? 2 : 1, type); String ponyRes = String.format("%s:textures/models/armor/%s_layer_%s%s.png", domain, texture, layer.name().toLowerCase(), type);
String oldPonyRes = String.format("%s:textures/models/armor/%s_layer_%d%s.png", domain, texture, layer == ArmorLayer.INNER ? 2 : 1, type);
ponyRes = getArmorTexture(entity, itemstack, ponyRes, slot, type); ResourceLocation human = getArmorTexture(entity, itemstack, ponyRes, slot, type);
ResourceLocation oldPony = ponifyResource(getArmorTexture(entity, itemstack, oldPonyRes, slot, type));
ResourceLocation human = getHumanResource(ponyRes); ResourceLocation pony = ponifyResource(human);
ResourceLocation pony = getPonyResource(human);
// check resource packs for either texture. // check resource packs for either texture.
for (ResourcePackRepository.Entry entry : Minecraft.getMinecraft().getResourcePackRepository().getRepositoryEntries()) { for (ResourcePackRepository.Entry entry : Minecraft.getMinecraft().getResourcePackRepository().getRepositoryEntries()) {
if (entry.getResourcePack().resourceExists(pony)) { if (entry.getResourcePack().resourceExists(pony)) {
// ponies are more important // ponies are more important
return new Tuple<>(pony, true); return new Tuple<>(pony, true);
} else if (entry.getResourcePack().resourceExists(oldPony)) {
return new Tuple<>(oldPony, true);
} else if (entry.getResourcePack().resourceExists(human)) { } else if (entry.getResourcePack().resourceExists(human)) {
// but I guess I'll take a human // but I guess I'll take a human
return new Tuple<>(human, false); return new Tuple<>(human, false);
} }
} }
// the default pack // the default pack
try { try {
Minecraft.getMinecraft().getResourceManager().getResource(pony); Minecraft.getMinecraft().getResourceManager().getResource(pony);
return new Tuple<>(pony, true); return new Tuple<>(pony, true);
} catch (IOException e) { } catch (IOException e) {
try {
Minecraft.getMinecraft().getResourceManager().getResource(oldPony);
return new Tuple<>(oldPony, true);
} catch (IOException r) {
return new Tuple<>(human, false); return new Tuple<>(human, false);
} }
} }
private <V extends ModelBiped & IModelArmor> void prepareToRender(V model, EntityEquipmentSlot slot, boolean isPony) {
model.setVisible(false);
switch (slot) {
case HEAD:
model.showHead(isPony);
break;
case FEET:
model.showFeet(true);
break;
case LEGS:
model.showFeet(true);
model.showLegs(isPony);
case CHEST:
model.showSaddle(isPony);
default:
}
} }
private static ResourceLocation getHumanResource(String resource) { private static ResourceLocation ponifyResource(ResourceLocation human) {
return HUMAN_ARMOUR.computeIfAbsent(resource, ResourceLocation::new);
}
private static ResourceLocation getPonyResource(ResourceLocation human) {
return PONY_ARMOUR.computeIfAbsent(human, key -> { return PONY_ARMOUR.computeIfAbsent(human, key -> {
String domain = human.getNamespace(); String domain = human.getNamespace();
if ("minecraft".equals(domain)) { if ("minecraft".equals(domain)) {
@ -157,11 +147,11 @@ public class LayerPonyArmor<T extends EntityLivingBase> extends AbstractPonyLaye
}); });
} }
private static String getArmorTexture(EntityLivingBase entity, ItemStack item, String def, EntityEquipmentSlot slot, @Nullable String type) { private static ResourceLocation getArmorTexture(EntityLivingBase entity, ItemStack item, String def, EntityEquipmentSlot slot, @Nullable String type) {
return ForgeProxy.getArmorTexture(entity, item, def, slot, type); return HUMAN_ARMOUR.computeIfAbsent(ForgeProxy.getArmorTexture(entity, item, def, slot, type), ResourceLocation::new);
} }
private static ModelPonyArmor getArmorModel(EntityLivingBase entity, ItemStack itemstack, EntityEquipmentSlot slot, ModelPonyArmor def) { private static ModelPonyArmor getArmorModel(EntityLivingBase entity, ItemStack itemstack, EntityEquipmentSlot slot, ArmorLayer layer, ModelPonyArmor def) {
ModelBase model = ForgeProxy.getArmorModel(entity, itemstack, slot, def); ModelBase model = ForgeProxy.getArmorModel(entity, itemstack, slot, def);
if (model instanceof ModelPonyArmor) { if (model instanceof ModelPonyArmor) {
@ -169,7 +159,7 @@ public class LayerPonyArmor<T extends EntityLivingBase> extends AbstractPonyLaye
} }
if (model instanceof IEquestrianArmor) { if (model instanceof IEquestrianArmor) {
return ((IEquestrianArmor) model).getArmorForSlot(slot); return ((IEquestrianArmor) model).getArmorForLayer(layer);
} }
return def; return def;

View file

@ -15,6 +15,7 @@ import com.minelittlepony.render.RenderPony;
import com.minelittlepony.render.PonySkullRenderer.ISkull; import com.minelittlepony.render.PonySkullRenderer.ISkull;
import com.minelittlepony.render.layer.LayerEntityOnPonyShoulder; import com.minelittlepony.render.layer.LayerEntityOnPonyShoulder;
import com.minelittlepony.render.layer.LayerHeldPonyItemMagical; import com.minelittlepony.render.layer.LayerHeldPonyItemMagical;
import com.minelittlepony.render.layer.LayerPonyArmor;
import com.minelittlepony.render.layer.LayerPonyCape; import com.minelittlepony.render.layer.LayerPonyCape;
import com.minelittlepony.render.layer.LayerPonyCustomHead; import com.minelittlepony.render.layer.LayerPonyCustomHead;
import com.minelittlepony.render.layer.LayerPonyElytra; import com.minelittlepony.render.layer.LayerPonyElytra;
@ -95,6 +96,7 @@ public class RenderPonyPlayer extends RenderPlayer implements IRenderPony<Abstra
protected void addLayers() { protected void addLayers() {
layerRenderers.clear(); layerRenderers.clear();
addLayer(new LayerPonyArmor<>(this));
addLayer(new LayerArrow(this)); addLayer(new LayerArrow(this));
addLayer(new LayerPonyCustomHead<>(this)); addLayer(new LayerPonyCustomHead<>(this));
addLayer(new LayerPonyElytra<>(this)); addLayer(new LayerPonyElytra<>(this));

View file

@ -44,8 +44,8 @@ public class RenderPonySkeleton<Skeleton extends AbstractSkeleton> extends Rende
addLayer(new LayerBipedArmor(this) { addLayer(new LayerBipedArmor(this) {
@Override @Override
protected void initArmor() { protected void initArmor() {
modelLeggings = getModelWrapper().getArmor().leggings; modelLeggings = getModelWrapper().getArmor().innerLayer;
modelArmor = getModelWrapper().getArmor().chestplate; modelArmor = getModelWrapper().getArmor().outerLayer;
} }
}); });
} }