001package net.minecraft.item;
002
003import cpw.mods.fml.relauncher.Side;
004import cpw.mods.fml.relauncher.SideOnly;
005import java.util.ArrayList;
006import java.util.HashMap;
007import java.util.Iterator;
008import java.util.LinkedHashMap;
009import java.util.List;
010import java.util.Map;
011import net.minecraft.client.renderer.texture.IconRegister;
012import net.minecraft.creativetab.CreativeTabs;
013import net.minecraft.entity.player.EntityPlayer;
014import net.minecraft.entity.projectile.EntityPotion;
015import net.minecraft.nbt.NBTTagCompound;
016import net.minecraft.nbt.NBTTagList;
017import net.minecraft.potion.Potion;
018import net.minecraft.potion.PotionEffect;
019import net.minecraft.potion.PotionHelper;
020import net.minecraft.util.EnumChatFormatting;
021import net.minecraft.util.Icon;
022import net.minecraft.util.StatCollector;
023import net.minecraft.world.World;
024
025public class ItemPotion extends Item
026{
027    /** maps potion damage values to lists of effect names */
028    private HashMap effectCache = new HashMap();
029    private static final Map field_77835_b = new LinkedHashMap();
030    @SideOnly(Side.CLIENT)
031    private Icon field_94591_c;
032    @SideOnly(Side.CLIENT)
033    private Icon field_94590_d;
034    @SideOnly(Side.CLIENT)
035    private Icon field_94592_ct;
036
037    public ItemPotion(int par1)
038    {
039        super(par1);
040        this.setMaxStackSize(1);
041        this.setHasSubtypes(true);
042        this.setMaxDamage(0);
043        this.setCreativeTab(CreativeTabs.tabBrewing);
044    }
045
046    /**
047     * Returns a list of potion effects for the specified itemstack.
048     */
049    public List getEffects(ItemStack par1ItemStack)
050    {
051        if (par1ItemStack.hasTagCompound() && par1ItemStack.getTagCompound().hasKey("CustomPotionEffects"))
052        {
053            ArrayList arraylist = new ArrayList();
054            NBTTagList nbttaglist = par1ItemStack.getTagCompound().getTagList("CustomPotionEffects");
055
056            for (int i = 0; i < nbttaglist.tagCount(); ++i)
057            {
058                NBTTagCompound nbttagcompound = (NBTTagCompound)nbttaglist.tagAt(i);
059                arraylist.add(PotionEffect.readCustomPotionEffectFromNBT(nbttagcompound));
060            }
061
062            return arraylist;
063        }
064        else
065        {
066            List list = (List)this.effectCache.get(Integer.valueOf(par1ItemStack.getItemDamage()));
067
068            if (list == null)
069            {
070                list = PotionHelper.getPotionEffects(par1ItemStack.getItemDamage(), false);
071                this.effectCache.put(Integer.valueOf(par1ItemStack.getItemDamage()), list);
072            }
073
074            return list;
075        }
076    }
077
078    /**
079     * Returns a list of effects for the specified potion damage value.
080     */
081    public List getEffects(int par1)
082    {
083        List list = (List)this.effectCache.get(Integer.valueOf(par1));
084
085        if (list == null)
086        {
087            list = PotionHelper.getPotionEffects(par1, false);
088            this.effectCache.put(Integer.valueOf(par1), list);
089        }
090
091        return list;
092    }
093
094    public ItemStack onEaten(ItemStack par1ItemStack, World par2World, EntityPlayer par3EntityPlayer)
095    {
096        if (!par3EntityPlayer.capabilities.isCreativeMode)
097        {
098            --par1ItemStack.stackSize;
099        }
100
101        if (!par2World.isRemote)
102        {
103            List list = this.getEffects(par1ItemStack);
104
105            if (list != null)
106            {
107                Iterator iterator = list.iterator();
108
109                while (iterator.hasNext())
110                {
111                    PotionEffect potioneffect = (PotionEffect)iterator.next();
112                    par3EntityPlayer.addPotionEffect(new PotionEffect(potioneffect));
113                }
114            }
115        }
116
117        if (!par3EntityPlayer.capabilities.isCreativeMode)
118        {
119            if (par1ItemStack.stackSize <= 0)
120            {
121                return new ItemStack(Item.glassBottle);
122            }
123
124            par3EntityPlayer.inventory.addItemStackToInventory(new ItemStack(Item.glassBottle));
125        }
126
127        return par1ItemStack;
128    }
129
130    /**
131     * How long it takes to use or consume an item
132     */
133    public int getMaxItemUseDuration(ItemStack par1ItemStack)
134    {
135        return 32;
136    }
137
138    /**
139     * returns the action that specifies what animation to play when the items is being used
140     */
141    public EnumAction getItemUseAction(ItemStack par1ItemStack)
142    {
143        return EnumAction.drink;
144    }
145
146    /**
147     * Called whenever this item is equipped and the right mouse button is pressed. Args: itemStack, world, entityPlayer
148     */
149    public ItemStack onItemRightClick(ItemStack par1ItemStack, World par2World, EntityPlayer par3EntityPlayer)
150    {
151        if (isSplash(par1ItemStack.getItemDamage()))
152        {
153            if (!par3EntityPlayer.capabilities.isCreativeMode)
154            {
155                --par1ItemStack.stackSize;
156            }
157
158            par2World.playSoundAtEntity(par3EntityPlayer, "random.bow", 0.5F, 0.4F / (itemRand.nextFloat() * 0.4F + 0.8F));
159
160            if (!par2World.isRemote)
161            {
162                par2World.spawnEntityInWorld(new EntityPotion(par2World, par3EntityPlayer, par1ItemStack));
163            }
164
165            return par1ItemStack;
166        }
167        else
168        {
169            par3EntityPlayer.setItemInUse(par1ItemStack, this.getMaxItemUseDuration(par1ItemStack));
170            return par1ItemStack;
171        }
172    }
173
174    /**
175     * Callback for item usage. If the item does something special on right clicking, he will have one of those. Return
176     * True if something happen and false if it don't. This is for ITEMS, not BLOCKS
177     */
178    public boolean onItemUse(ItemStack par1ItemStack, EntityPlayer par2EntityPlayer, World par3World, int par4, int par5, int par6, int par7, float par8, float par9, float par10)
179    {
180        return false;
181    }
182
183    @SideOnly(Side.CLIENT)
184
185    /**
186     * Gets an icon index based on an item's damage value
187     */
188    public Icon getIconFromDamage(int par1)
189    {
190        return isSplash(par1) ? this.field_94591_c : this.field_94590_d;
191    }
192
193    @SideOnly(Side.CLIENT)
194
195    /**
196     * Gets an icon index based on an item's damage value and the given render pass
197     */
198    public Icon getIconFromDamageForRenderPass(int par1, int par2)
199    {
200        return par2 == 0 ? this.field_94592_ct : super.getIconFromDamageForRenderPass(par1, par2);
201    }
202
203    /**
204     * returns wether or not a potion is a throwable splash potion based on damage value
205     */
206    public static boolean isSplash(int par0)
207    {
208        return (par0 & 16384) != 0;
209    }
210
211    @SideOnly(Side.CLIENT)
212    public int getColorFromDamage(int par1)
213    {
214        return PotionHelper.func_77915_a(par1, false);
215    }
216
217    @SideOnly(Side.CLIENT)
218    public int getColorFromItemStack(ItemStack par1ItemStack, int par2)
219    {
220        return par2 > 0 ? 16777215 : this.getColorFromDamage(par1ItemStack.getItemDamage());
221    }
222
223    @SideOnly(Side.CLIENT)
224    public boolean requiresMultipleRenderPasses()
225    {
226        return true;
227    }
228
229    @SideOnly(Side.CLIENT)
230    public boolean isEffectInstant(int par1)
231    {
232        List list = this.getEffects(par1);
233
234        if (list != null && !list.isEmpty())
235        {
236            Iterator iterator = list.iterator();
237            PotionEffect potioneffect;
238
239            do
240            {
241                if (!iterator.hasNext())
242                {
243                    return false;
244                }
245
246                potioneffect = (PotionEffect)iterator.next();
247            }
248            while (!Potion.potionTypes[potioneffect.getPotionID()].isInstant());
249
250            return true;
251        }
252        else
253        {
254            return false;
255        }
256    }
257
258    public String getItemDisplayName(ItemStack par1ItemStack)
259    {
260        if (par1ItemStack.getItemDamage() == 0)
261        {
262            return StatCollector.translateToLocal("item.emptyPotion.name").trim();
263        }
264        else
265        {
266            String s = "";
267
268            if (isSplash(par1ItemStack.getItemDamage()))
269            {
270                s = StatCollector.translateToLocal("potion.prefix.grenade").trim() + " ";
271            }
272
273            List list = Item.potion.getEffects(par1ItemStack);
274            String s1;
275
276            if (list != null && !list.isEmpty())
277            {
278                s1 = ((PotionEffect)list.get(0)).getEffectName();
279                s1 = s1 + ".postfix";
280                return s + StatCollector.translateToLocal(s1).trim();
281            }
282            else
283            {
284                s1 = PotionHelper.func_77905_c(par1ItemStack.getItemDamage());
285                return StatCollector.translateToLocal(s1).trim() + " " + super.getItemDisplayName(par1ItemStack);
286            }
287        }
288    }
289
290    @SideOnly(Side.CLIENT)
291
292    /**
293     * allows items to add custom lines of information to the mouseover description
294     */
295    public void addInformation(ItemStack par1ItemStack, EntityPlayer par2EntityPlayer, List par3List, boolean par4)
296    {
297        if (par1ItemStack.getItemDamage() != 0)
298        {
299            List list1 = Item.potion.getEffects(par1ItemStack);
300
301            if (list1 != null && !list1.isEmpty())
302            {
303                Iterator iterator = list1.iterator();
304
305                while (iterator.hasNext())
306                {
307                    PotionEffect potioneffect = (PotionEffect)iterator.next();
308                    String s = StatCollector.translateToLocal(potioneffect.getEffectName()).trim();
309
310                    if (potioneffect.getAmplifier() > 0)
311                    {
312                        s = s + " " + StatCollector.translateToLocal("potion.potency." + potioneffect.getAmplifier()).trim();
313                    }
314
315                    if (potioneffect.getDuration() > 20)
316                    {
317                        s = s + " (" + Potion.getDurationString(potioneffect) + ")";
318                    }
319
320                    if (Potion.potionTypes[potioneffect.getPotionID()].isBadEffect())
321                    {
322                        par3List.add(EnumChatFormatting.RED + s);
323                    }
324                    else
325                    {
326                        par3List.add(EnumChatFormatting.GRAY + s);
327                    }
328                }
329            }
330            else
331            {
332                String s1 = StatCollector.translateToLocal("potion.empty").trim();
333                par3List.add(EnumChatFormatting.GRAY + s1);
334            }
335        }
336    }
337
338    @SideOnly(Side.CLIENT)
339    public boolean hasEffect(ItemStack par1ItemStack)
340    {
341        List list = this.getEffects(par1ItemStack);
342        return list != null && !list.isEmpty();
343    }
344
345    @SideOnly(Side.CLIENT)
346
347    /**
348     * returns a list of items with the same ID, but different meta (eg: dye returns 16 items)
349     */
350    public void getSubItems(int par1, CreativeTabs par2CreativeTabs, List par3List)
351    {
352        super.getSubItems(par1, par2CreativeTabs, par3List);
353        int j;
354
355        if (field_77835_b.isEmpty())
356        {
357            for (int k = 0; k <= 15; ++k)
358            {
359                for (j = 0; j <= 1; ++j)
360                {
361                    int l;
362
363                    if (j == 0)
364                    {
365                        l = k | 8192;
366                    }
367                    else
368                    {
369                        l = k | 16384;
370                    }
371
372                    for (int i1 = 0; i1 <= 2; ++i1)
373                    {
374                        int j1 = l;
375
376                        if (i1 != 0)
377                        {
378                            if (i1 == 1)
379                            {
380                                j1 = l | 32;
381                            }
382                            else if (i1 == 2)
383                            {
384                                j1 = l | 64;
385                            }
386                        }
387
388                        List list1 = PotionHelper.getPotionEffects(j1, false);
389
390                        if (list1 != null && !list1.isEmpty())
391                        {
392                            field_77835_b.put(list1, Integer.valueOf(j1));
393                        }
394                    }
395                }
396            }
397        }
398
399        Iterator iterator = field_77835_b.values().iterator();
400
401        while (iterator.hasNext())
402        {
403            j = ((Integer)iterator.next()).intValue();
404            par3List.add(new ItemStack(par1, 1, j));
405        }
406    }
407
408    @SideOnly(Side.CLIENT)
409    public void updateIcons(IconRegister par1IconRegister)
410    {
411        this.field_94590_d = par1IconRegister.registerIcon("potion");
412        this.field_94591_c = par1IconRegister.registerIcon("potion_splash");
413        this.field_94592_ct = par1IconRegister.registerIcon("potion_contents");
414    }
415
416    @SideOnly(Side.CLIENT)
417    public static Icon func_94589_d(String par0Str)
418    {
419        return par0Str == "potion" ? Item.potion.field_94590_d : (par0Str == "potion_splash" ? Item.potion.field_94591_c : (par0Str == "potion_contents" ? Item.potion.field_94592_ct : null));
420    }
421}