001    package net.minecraft.src;
002    
003    import cpw.mods.fml.common.Side;
004    import cpw.mods.fml.common.asm.SideOnly;
005    import java.util.Iterator;
006    import java.util.List;
007    import java.util.Random;
008    
009    public class ContainerEnchantment extends Container
010    {
011        /** SlotEnchantmentTable object with ItemStack to be enchanted */
012        public IInventory tableInventory = new SlotEnchantmentTable(this, "Enchant", 1);
013    
014        /** current world (for bookshelf counting) */
015        private World worldPointer;
016        private int posX;
017        private int posY;
018        private int posZ;
019        private Random rand = new Random();
020    
021        /** used as seed for EnchantmentNameParts (see GuiEnchantment) */
022        public long nameSeed;
023    
024        /** 3-member array storing the enchantment levels of each slot */
025        public int[] enchantLevels = new int[3];
026    
027        public ContainerEnchantment(InventoryPlayer par1InventoryPlayer, World par2World, int par3, int par4, int par5)
028        {
029            this.worldPointer = par2World;
030            this.posX = par3;
031            this.posY = par4;
032            this.posZ = par5;
033            this.addSlotToContainer(new SlotEnchantment(this, this.tableInventory, 0, 25, 47));
034            int var6;
035    
036            for (var6 = 0; var6 < 3; ++var6)
037            {
038                for (int var7 = 0; var7 < 9; ++var7)
039                {
040                    this.addSlotToContainer(new Slot(par1InventoryPlayer, var7 + var6 * 9 + 9, 8 + var7 * 18, 84 + var6 * 18));
041                }
042            }
043    
044            for (var6 = 0; var6 < 9; ++var6)
045            {
046                this.addSlotToContainer(new Slot(par1InventoryPlayer, var6, 8 + var6 * 18, 142));
047            }
048        }
049    
050        public void addCraftingToCrafters(ICrafting par1ICrafting)
051        {
052            super.addCraftingToCrafters(par1ICrafting);
053            par1ICrafting.updateCraftingInventoryInfo(this, 0, this.enchantLevels[0]);
054            par1ICrafting.updateCraftingInventoryInfo(this, 1, this.enchantLevels[1]);
055            par1ICrafting.updateCraftingInventoryInfo(this, 2, this.enchantLevels[2]);
056        }
057    
058        /**
059         * Updates crafting matrix; called from onCraftMatrixChanged. Args: none
060         */
061        public void updateCraftingResults()
062        {
063            super.updateCraftingResults();
064    
065            for (int var1 = 0; var1 < this.crafters.size(); ++var1)
066            {
067                ICrafting var2 = (ICrafting)this.crafters.get(var1);
068                var2.updateCraftingInventoryInfo(this, 0, this.enchantLevels[0]);
069                var2.updateCraftingInventoryInfo(this, 1, this.enchantLevels[1]);
070                var2.updateCraftingInventoryInfo(this, 2, this.enchantLevels[2]);
071            }
072        }
073    
074        @SideOnly(Side.CLIENT)
075        public void updateProgressBar(int par1, int par2)
076        {
077            if (par1 >= 0 && par1 <= 2)
078            {
079                this.enchantLevels[par1] = par2;
080            }
081            else
082            {
083                super.updateProgressBar(par1, par2);
084            }
085        }
086    
087        /**
088         * Callback for when the crafting matrix is changed.
089         */
090        public void onCraftMatrixChanged(IInventory par1IInventory)
091        {
092            if (par1IInventory == this.tableInventory)
093            {
094                ItemStack var2 = par1IInventory.getStackInSlot(0);
095                int var3;
096    
097                if (var2 != null && var2.isItemEnchantable())
098                {
099                    this.nameSeed = this.rand.nextLong();
100    
101                    if (!this.worldPointer.isRemote)
102                    {
103                        var3 = 0;
104                        int var4;
105    
106                        for (var4 = -1; var4 <= 1; ++var4)
107                        {
108                            for (int var5 = -1; var5 <= 1; ++var5)
109                            {
110                                if ((var4 != 0 || var5 != 0) && this.worldPointer.isAirBlock(this.posX + var5, this.posY, this.posZ + var4) && this.worldPointer.isAirBlock(this.posX + var5, this.posY + 1, this.posZ + var4))
111                                {
112                                    if (this.worldPointer.getBlockId(this.posX + var5 * 2, this.posY, this.posZ + var4 * 2) == Block.bookShelf.blockID)
113                                    {
114                                        ++var3;
115                                    }
116    
117                                    if (this.worldPointer.getBlockId(this.posX + var5 * 2, this.posY + 1, this.posZ + var4 * 2) == Block.bookShelf.blockID)
118                                    {
119                                        ++var3;
120                                    }
121    
122                                    if (var5 != 0 && var4 != 0)
123                                    {
124                                        if (this.worldPointer.getBlockId(this.posX + var5 * 2, this.posY, this.posZ + var4) == Block.bookShelf.blockID)
125                                        {
126                                            ++var3;
127                                        }
128    
129                                        if (this.worldPointer.getBlockId(this.posX + var5 * 2, this.posY + 1, this.posZ + var4) == Block.bookShelf.blockID)
130                                        {
131                                            ++var3;
132                                        }
133    
134                                        if (this.worldPointer.getBlockId(this.posX + var5, this.posY, this.posZ + var4 * 2) == Block.bookShelf.blockID)
135                                        {
136                                            ++var3;
137                                        }
138    
139                                        if (this.worldPointer.getBlockId(this.posX + var5, this.posY + 1, this.posZ + var4 * 2) == Block.bookShelf.blockID)
140                                        {
141                                            ++var3;
142                                        }
143                                    }
144                                }
145                            }
146                        }
147    
148                        for (var4 = 0; var4 < 3; ++var4)
149                        {
150                            this.enchantLevels[var4] = EnchantmentHelper.calcItemStackEnchantability(this.rand, var4, var3, var2);
151                        }
152    
153                        this.updateCraftingResults();
154                    }
155                }
156                else
157                {
158                    for (var3 = 0; var3 < 3; ++var3)
159                    {
160                        this.enchantLevels[var3] = 0;
161                    }
162                }
163            }
164        }
165    
166        /**
167         * enchants the item on the table using the specified slot; also deducts XP from player
168         */
169        public boolean enchantItem(EntityPlayer par1EntityPlayer, int par2)
170        {
171            ItemStack var3 = this.tableInventory.getStackInSlot(0);
172    
173            if (this.enchantLevels[par2] > 0 && var3 != null && (par1EntityPlayer.experienceLevel >= this.enchantLevels[par2] || par1EntityPlayer.capabilities.isCreativeMode))
174            {
175                if (!this.worldPointer.isRemote)
176                {
177                    List var4 = EnchantmentHelper.buildEnchantmentList(this.rand, var3, this.enchantLevels[par2]);
178    
179                    if (var4 != null)
180                    {
181                        par1EntityPlayer.addExperienceLevel(-this.enchantLevels[par2]);
182                        Iterator var5 = var4.iterator();
183    
184                        while (var5.hasNext())
185                        {
186                            EnchantmentData var6 = (EnchantmentData)var5.next();
187                            var3.addEnchantment(var6.enchantmentobj, var6.enchantmentLevel);
188                        }
189    
190                        this.onCraftMatrixChanged(this.tableInventory);
191                    }
192                }
193    
194                return true;
195            }
196            else
197            {
198                return false;
199            }
200        }
201    
202        /**
203         * Callback for when the crafting gui is closed.
204         */
205        public void onCraftGuiClosed(EntityPlayer par1EntityPlayer)
206        {
207            super.onCraftGuiClosed(par1EntityPlayer);
208    
209            if (!this.worldPointer.isRemote)
210            {
211                ItemStack var2 = this.tableInventory.getStackInSlotOnClosing(0);
212    
213                if (var2 != null)
214                {
215                    par1EntityPlayer.dropPlayerItem(var2);
216                }
217            }
218        }
219    
220        public boolean canInteractWith(EntityPlayer par1EntityPlayer)
221        {
222            return this.worldPointer.getBlockId(this.posX, this.posY, this.posZ) != Block.enchantmentTable.blockID ? false : par1EntityPlayer.getDistanceSq((double)this.posX + 0.5D, (double)this.posY + 0.5D, (double)this.posZ + 0.5D) <= 64.0D;
223        }
224    
225        /**
226         * Called when a player shift-clicks on a slot. You must override this or you will crash when someone does that.
227         */
228        public ItemStack transferStackInSlot(EntityPlayer par1EntityPlayer, int par2)
229        {
230            ItemStack var3 = null;
231            Slot var4 = (Slot)this.inventorySlots.get(par2);
232    
233            if (var4 != null && var4.getHasStack())
234            {
235                ItemStack var5 = var4.getStack();
236                var3 = var5.copy();
237    
238                if (par2 == 0)
239                {
240                    if (!this.mergeItemStack(var5, 1, 37, true))
241                    {
242                        return null;
243                    }
244                }
245                else
246                {
247                    if (((Slot)this.inventorySlots.get(0)).getHasStack() || !((Slot)this.inventorySlots.get(0)).isItemValid(var5))
248                    {
249                        return null;
250                    }
251    
252                    if (var5.hasTagCompound() && var5.stackSize == 1)
253                    {
254                        ((Slot)this.inventorySlots.get(0)).putStack(var5.copy());
255                        var5.stackSize = 0;
256                    }
257                    else if (var5.stackSize >= 1)
258                    {
259                        ((Slot)this.inventorySlots.get(0)).putStack(new ItemStack(var5.itemID, 1, var5.getItemDamage()));
260                        --var5.stackSize;
261                    }
262                }
263    
264                if (var5.stackSize == 0)
265                {
266                    var4.putStack((ItemStack)null);
267                }
268                else
269                {
270                    var4.onSlotChanged();
271                }
272    
273                if (var5.stackSize == var3.stackSize)
274                {
275                    return null;
276                }
277    
278                var4.onPickupFromSlot(par1EntityPlayer, var5);
279            }
280    
281            return var3;
282        }
283    }