mojira.dev
MC-87048

Putting Design on Shield will cause Shield to lose Enchantment

Applying a design to a shield with an existing Enchantment with a banner causes the resulting shield to lose any enchantments that it had.


Code analysis by @unknown can be found in this comment.

Linked issues

Attachments

Comments 5

Confirmed even with Unbreaking 3.

Crafting has always removed enchantments.

Technically you're wrong because of MC-77432. I think it's not intended this way since you don't gain anything from changing the banner pattern. This isn't like repairing two shields together, this is purely visual with no gameplay advantage.

Confirmed for 16w06a

Please link to this comment in the description

The following is based on decompiled version of Minecraft 1.9 using MCP 9.24 beta. All method and class names are the names used in the decompiled version.

The reason why this happens is because the method net.minecraft.item.crafting.ShieldRecipes.Decoration.getCraftingResult(InventoryCrafting) is not using the data of the old shield.

public ItemStack getCraftingResult(InventoryCrafting inv)
{
    // Replaced this
    //ItemStack itemstack = null;
    //
    //for (int i = 0; i < inv.getSizeInventory(); ++i)
    //{
    //    ItemStack itemstack1 = inv.getStackInSlot(i);
    //
    //    if (itemstack1 != null && itemstack1.getItem() == Items.banner)
    //    {
    //        itemstack = itemstack1;
    //    }
    //}
    //
    //ItemStack itemstack2 = new ItemStack(Items.shield, 1, 0);
    //EnumDyeColor enumdyecolor;
    //NBTTagCompound nbttagcompound;
    //
    //if (itemstack.hasTagCompound())
    //{
    //    nbttagcompound = (NBTTagCompound)itemstack.getTagCompound().copy();
    //    enumdyecolor = EnumDyeColor.byDyeDamage(TileEntityBanner.getBaseColor(itemstack));
    //}
    //else
    //{
    //    nbttagcompound = new NBTTagCompound();
    //    enumdyecolor = EnumDyeColor.byDyeDamage(itemstack.getItemDamage());
    //}
    //
    //itemstack2.setTagCompound(nbttagcompound);
    //TileEntityBanner.func_184248_a(itemstack2, enumdyecolor);
    //return itemstack2;
    ItemStack itemStackBanner = null;
    ItemStack itemStackShieldOld = null;

    for (int i = 0; i < inv.getSizeInventory(); ++i)
    {
        ItemStack itemStackInSlot = inv.getStackInSlot(i);

        if (itemStackInSlot != null) {
            if (itemStackInSlot.getItem() == Items.banner) {
                itemStackBanner = itemStackInSlot;
            }
            else if (itemStackInSlot.getItem() == Items.shield) {
                itemStackShieldOld = itemStackInSlot;
            }
        }
    }
    
    ItemStack itemStackShield = new ItemStack(Items.shield, 1, itemStackShieldOld.getMetadata());
    if (itemStackShieldOld.hasTagCompound()) {
        itemStackShield.setTagCompound((NBTTagCompound) itemStackShieldOld.getTagCompound().copy());
    }
    
    /*
     * The method {@link net.minecraft.tileentity.TileEntityBanner#getBaseColor(ItemStack)} calls {@link net.minecraft.item.ItemStack#getMetadata()}
     * whereas this method used to call {@link net.minecraft.item.ItemStack#getItemDamage()} if no "BlockEntityTag" tag exists
     */
    EnumDyeColor dyeColorBanner = EnumDyeColor.byDyeDamage(TileEntityBanner.getBaseColor(itemStackBanner));
    NBTTagCompound nbtTagCompoundBanner = itemStackBanner.getSubCompound("BlockEntityTag", false);
    
    if (nbtTagCompoundBanner != null) {
        itemStackShield.setTagInfo("BlockEntityTag", nbtTagCompoundBanner);
    }
    TileEntityBanner.func_184248_a(itemStackShield, dyeColorBanner);
    return itemStackShield;
}

Note: This fix would also fix MC-100770

Patrick Rye

Agnes Larsson

Confirmed

Minecraft 15w34d, Minecraft 15w44b, Minecraft 16w06a

Minecraft 16w33a

Retrieved