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.List;
006
007 public class ItemMap extends ItemMapBase
008 {
009 protected ItemMap(int par1)
010 {
011 super(par1);
012 this.setHasSubtypes(true);
013 }
014
015 @SideOnly(Side.CLIENT)
016 public static MapData getMPMapData(short par0, World par1World)
017 {
018 String var2 = "map_" + par0;
019 MapData var3 = (MapData)par1World.loadItemData(MapData.class, var2);
020
021 if (var3 == null)
022 {
023 var3 = new MapData(var2);
024 par1World.setItemData(var2, var3);
025 }
026
027 return var3;
028 }
029
030 public MapData getMapData(ItemStack par1ItemStack, World par2World)
031 {
032 String var3 = "map_" + par1ItemStack.getItemDamage();
033 MapData var4 = (MapData)par2World.loadItemData(MapData.class, var3);
034
035 if (var4 == null && !par2World.isRemote)
036 {
037 par1ItemStack.setItemDamage(par2World.getUniqueDataId("map"));
038 var3 = "map_" + par1ItemStack.getItemDamage();
039 var4 = new MapData(var3);
040 var4.scale = 3;
041 int var5 = 128 * (1 << var4.scale);
042 var4.xCenter = Math.round((float)par2World.getWorldInfo().getSpawnX() / (float)var5) * var5;
043 var4.zCenter = Math.round((float)(par2World.getWorldInfo().getSpawnZ() / var5)) * var5;
044 var4.dimension = par2World.provider.dimensionId;
045 var4.markDirty();
046 par2World.setItemData(var3, var4);
047 }
048
049 return var4;
050 }
051
052 public void updateMapData(World par1World, Entity par2Entity, MapData par3MapData)
053 {
054 if (par1World.provider.dimensionId == par3MapData.dimension && par2Entity instanceof EntityPlayer)
055 {
056 short var4 = 128;
057 short var5 = 128;
058 int var6 = 1 << par3MapData.scale;
059 int var7 = par3MapData.xCenter;
060 int var8 = par3MapData.zCenter;
061 int var9 = MathHelper.floor_double(par2Entity.posX - (double)var7) / var6 + var4 / 2;
062 int var10 = MathHelper.floor_double(par2Entity.posZ - (double)var8) / var6 + var5 / 2;
063 int var11 = 128 / var6;
064
065 if (par1World.provider.hasNoSky)
066 {
067 var11 /= 2;
068 }
069
070 MapInfo var12 = par3MapData.func_82568_a((EntityPlayer)par2Entity);
071 ++var12.field_82569_d;
072
073 for (int var13 = var9 - var11 + 1; var13 < var9 + var11; ++var13)
074 {
075 if ((var13 & 15) == (var12.field_82569_d & 15))
076 {
077 int var14 = 255;
078 int var15 = 0;
079 double var16 = 0.0D;
080
081 for (int var18 = var10 - var11 - 1; var18 < var10 + var11; ++var18)
082 {
083 if (var13 >= 0 && var18 >= -1 && var13 < var4 && var18 < var5)
084 {
085 int var19 = var13 - var9;
086 int var20 = var18 - var10;
087 boolean var21 = var19 * var19 + var20 * var20 > (var11 - 2) * (var11 - 2);
088 int var22 = (var7 / var6 + var13 - var4 / 2) * var6;
089 int var23 = (var8 / var6 + var18 - var5 / 2) * var6;
090 int[] var24 = new int[Block.blocksList.length];
091 Chunk var25 = par1World.getChunkFromBlockCoords(var22, var23);
092
093 if (!var25.isEmpty())
094 {
095 int var26 = var22 & 15;
096 int var27 = var23 & 15;
097 int var28 = 0;
098 double var29 = 0.0D;
099 int var31;
100 int var32;
101 int var33;
102 int var36;
103
104 if (par1World.provider.hasNoSky)
105 {
106 var31 = var22 + var23 * 231871;
107 var31 = var31 * var31 * 31287121 + var31 * 11;
108
109 if ((var31 >> 20 & 1) == 0)
110 {
111 var24[Block.dirt.blockID] += 10;
112 }
113 else
114 {
115 var24[Block.stone.blockID] += 10;
116 }
117
118 var29 = 100.0D;
119 }
120 else
121 {
122 for (var31 = 0; var31 < var6; ++var31)
123 {
124 for (var32 = 0; var32 < var6; ++var32)
125 {
126 var33 = var25.getHeightValue(var31 + var26, var32 + var27) + 1;
127 int var34 = 0;
128
129 if (var33 > 1)
130 {
131 boolean var35;
132
133 do
134 {
135 var35 = true;
136 var34 = var25.getBlockID(var31 + var26, var33 - 1, var32 + var27);
137
138 if (var34 == 0)
139 {
140 var35 = false;
141 }
142 else if (var33 > 0 && var34 > 0 && Block.blocksList[var34].blockMaterial.materialMapColor == MapColor.airColor)
143 {
144 var35 = false;
145 }
146
147 if (!var35)
148 {
149 --var33;
150
151 if (var33 <= 0)
152 {
153 break;
154 }
155
156 var34 = var25.getBlockID(var31 + var26, var33 - 1, var32 + var27);
157 }
158 }
159 while (var33 > 0 && !var35);
160
161 if (var33 > 0 && var34 != 0 && Block.blocksList[var34].blockMaterial.isLiquid())
162 {
163 var36 = var33 - 1;
164 boolean var37 = false;
165 int var43;
166
167 do
168 {
169 var43 = var25.getBlockID(var31 + var26, var36--, var32 + var27);
170 ++var28;
171 }
172 while (var36 > 0 && var43 != 0 && Block.blocksList[var43].blockMaterial.isLiquid());
173 }
174 }
175
176 var29 += (double)var33 / (double)(var6 * var6);
177 ++var24[var34];
178 }
179 }
180 }
181
182 var28 /= var6 * var6;
183 var31 = 0;
184 var32 = 0;
185
186 for (var33 = 0; var33 < Block.blocksList.length; ++var33)
187 {
188 if (var24[var33] > var31)
189 {
190 var32 = var33;
191 var31 = var24[var33];
192 }
193 }
194
195 double var40 = (var29 - var16) * 4.0D / (double)(var6 + 4) + ((double)(var13 + var18 & 1) - 0.5D) * 0.4D;
196 byte var39 = 1;
197
198 if (var40 > 0.6D)
199 {
200 var39 = 2;
201 }
202
203 if (var40 < -0.6D)
204 {
205 var39 = 0;
206 }
207
208 var36 = 0;
209
210 if (var32 > 0)
211 {
212 MapColor var42 = Block.blocksList[var32].blockMaterial.materialMapColor;
213
214 if (var42 == MapColor.waterColor)
215 {
216 var40 = (double)var28 * 0.1D + (double)(var13 + var18 & 1) * 0.2D;
217 var39 = 1;
218
219 if (var40 < 0.5D)
220 {
221 var39 = 2;
222 }
223
224 if (var40 > 0.9D)
225 {
226 var39 = 0;
227 }
228 }
229
230 var36 = var42.colorIndex;
231 }
232
233 var16 = var29;
234
235 if (var18 >= 0 && var19 * var19 + var20 * var20 < var11 * var11 && (!var21 || (var13 + var18 & 1) != 0))
236 {
237 byte var41 = par3MapData.colors[var13 + var18 * var4];
238 byte var38 = (byte)(var36 * 4 + var39);
239
240 if (var41 != var38)
241 {
242 if (var14 > var18)
243 {
244 var14 = var18;
245 }
246
247 if (var15 < var18)
248 {
249 var15 = var18;
250 }
251
252 par3MapData.colors[var13 + var18 * var4] = var38;
253 }
254 }
255 }
256 }
257 }
258
259 if (var14 <= var15)
260 {
261 par3MapData.func_76194_a(var13, var14, var15);
262 }
263 }
264 }
265 }
266 }
267
268 /**
269 * Called each tick as long the item is on a player inventory. Uses by maps to check if is on a player hand and
270 * update it's contents.
271 */
272 public void onUpdate(ItemStack par1ItemStack, World par2World, Entity par3Entity, int par4, boolean par5)
273 {
274 if (!par2World.isRemote)
275 {
276 MapData var6 = this.getMapData(par1ItemStack, par2World);
277
278 if (par3Entity instanceof EntityPlayer)
279 {
280 EntityPlayer var7 = (EntityPlayer)par3Entity;
281 var6.updateVisiblePlayers(var7, par1ItemStack);
282 }
283
284 if (par5)
285 {
286 this.updateMapData(par2World, par3Entity, var6);
287 }
288 }
289 }
290
291 /**
292 * returns null if no update is to be sent
293 */
294 public Packet createMapDataPacket(ItemStack par1ItemStack, World par2World, EntityPlayer par3EntityPlayer)
295 {
296 byte[] var4 = this.getMapData(par1ItemStack, par2World).func_76193_a(par1ItemStack, par2World, par3EntityPlayer);
297 return var4 == null ? null : new Packet131MapData((short)Item.map.shiftedIndex, (short)par1ItemStack.getItemDamage(), var4);
298 }
299
300 /**
301 * Called when item is crafted/smelted. Used only by maps so far.
302 */
303 public void onCreated(ItemStack par1ItemStack, World par2World, EntityPlayer par3EntityPlayer)
304 {
305 if (par1ItemStack.hasTagCompound() && par1ItemStack.getTagCompound().getBoolean("map_is_scaling"))
306 {
307 MapData var4 = Item.map.getMapData(par1ItemStack, par2World);
308 par1ItemStack.setItemDamage(par2World.getUniqueDataId("map"));
309 MapData var5 = new MapData("map_" + par1ItemStack.getItemDamage());
310 var5.scale = (byte)(var4.scale + 1);
311
312 if (var5.scale > 4)
313 {
314 var5.scale = 4;
315 }
316
317 var5.xCenter = var4.xCenter;
318 var5.zCenter = var4.zCenter;
319 var5.dimension = var4.dimension;
320 var5.markDirty();
321 par2World.setItemData("map_" + par1ItemStack.getItemDamage(), var5);
322 }
323 }
324
325 @SideOnly(Side.CLIENT)
326
327 /**
328 * allows items to add custom lines of information to the mouseover description
329 */
330 public void addInformation(ItemStack par1ItemStack, EntityPlayer par2EntityPlayer, List par3List, boolean par4)
331 {
332 MapData var5 = this.getMapData(par1ItemStack, par2EntityPlayer.worldObj);
333
334 if (par4)
335 {
336 if (var5 == null)
337 {
338 par3List.add("Unknown map");
339 }
340 else
341 {
342 par3List.add("Scaling at 1:" + (1 << var5.scale));
343 par3List.add("(Level " + var5.scale + "/" + 4 + ")");
344 }
345 }
346 }
347 }