001    /*
002     * The FML Forge Mod Loader suite. Copyright (C) 2012 cpw
003     *
004     * This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free
005     * Software Foundation; either version 2.1 of the License, or any later version.
006     *
007     * This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
008     * A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
009     *
010     * You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51
011     * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
012     */
013    package net.minecraft.src;
014    
015    import static cpw.mods.fml.relauncher.Side.CLIENT;
016    
017    import java.awt.image.BufferedImage;
018    import java.util.Collections;
019    import java.util.List;
020    import java.util.Map;
021    import java.util.logging.Logger;
022    
023    import net.minecraft.block.Block;
024    import net.minecraft.block.BlockDispenser;
025    import net.minecraft.client.*;
026    import net.minecraft.client.gui.GuiScreen;
027    import net.minecraft.client.multiplayer.NetClientHandler;
028    import net.minecraft.client.renderer.RenderBlocks;
029    import net.minecraft.client.renderer.RenderEngine;
030    import net.minecraft.client.renderer.entity.Render;
031    import net.minecraft.client.renderer.texturefx.TextureFX;
032    import net.minecraft.client.renderer.tileentity.TileEntitySpecialRenderer;
033    import net.minecraft.client.settings.KeyBinding;
034    import net.minecraft.command.ICommand;
035    import net.minecraft.dispenser.IBehaviorDispenseItem;
036    import net.minecraft.entity.Entity;
037    import net.minecraft.entity.EntityLiving;
038    import net.minecraft.entity.EnumCreatureType;
039    import net.minecraft.entity.player.EntityPlayer;
040    import net.minecraft.entity.player.EntityPlayerMP;
041    import net.minecraft.inventory.Container;
042    import net.minecraft.inventory.IInventory;
043    import net.minecraft.item.Item;
044    import net.minecraft.item.ItemBlock;
045    import net.minecraft.item.ItemStack;
046    import net.minecraft.network.NetServerHandler;
047    import net.minecraft.network.packet.Packet;
048    import net.minecraft.network.packet.Packet1Login;
049    import net.minecraft.network.packet.Packet250CustomPayload;
050    import net.minecraft.server.*;
051    import net.minecraft.stats.Achievement;
052    import net.minecraft.tileentity.TileEntity;
053    import net.minecraft.world.IBlockAccess;
054    import net.minecraft.world.World;
055    import net.minecraft.world.WorldType;
056    import net.minecraft.world.biome.BiomeGenBase;
057    import net.minecraft.world.chunk.IChunkProvider;
058    import cpw.mods.fml.client.FMLClientHandler;
059    import cpw.mods.fml.client.SpriteHelper;
060    import cpw.mods.fml.client.TextureFXManager;
061    import cpw.mods.fml.client.modloader.ModLoaderClientHelper;
062    import cpw.mods.fml.client.modloader.ModLoaderKeyBindingHandler;
063    import cpw.mods.fml.client.registry.ClientRegistry;
064    import cpw.mods.fml.client.registry.KeyBindingRegistry;
065    import cpw.mods.fml.client.registry.RenderingRegistry;
066    import cpw.mods.fml.common.FMLCommonHandler;
067    import cpw.mods.fml.common.FMLLog;
068    import cpw.mods.fml.common.Loader;
069    import cpw.mods.fml.common.ObfuscationReflectionHelper;
070    import cpw.mods.fml.common.modloader.ModLoaderHelper;
071    import cpw.mods.fml.common.modloader.ModLoaderModContainer;
072    import cpw.mods.fml.common.network.NetworkRegistry;
073    import cpw.mods.fml.common.network.PacketDispatcher;
074    import cpw.mods.fml.common.network.Player;
075    import cpw.mods.fml.common.registry.EntityRegistry;
076    import cpw.mods.fml.common.registry.GameRegistry;
077    import cpw.mods.fml.common.registry.LanguageRegistry;
078    import cpw.mods.fml.relauncher.SideOnly;
079    import cpw.mods.fml.server.FMLServerHandler;
080    
081    public class ModLoader
082    {
083        public static final String fmlMarker = "This is an FML marker";
084        // TODO dirty workaround for millinaire
085        @Deprecated
086        public static final Map<String,Map<String,String>> localizedStrings=Collections.emptyMap();
087    
088        /**
089         * Adds localization info for an achievement, Not used on the server.
090         *
091         * @param achievement The achievement to name
092         * @param name The name
093         * @param description The description
094         */
095        public static void addAchievementDesc(Achievement achievement, String name, String description)
096        {
097            String achName=achievement.getName();
098            addLocalization(achName, name);
099            addLocalization(achName+".desc", description);
100        }
101    
102        /**
103         * This method is a call in hook from modified external code. Implemented elsewhere.
104         *
105         * {@link GameRegistry#getFuelValue(ItemStack)}
106         *
107         * @param id The Item ID
108         * @param metadata The Item Metadata
109         * @return The fuel strength, in ticks, 0 if unhandled
110         */
111        @Deprecated
112        public static int addAllFuel(int id, int metadata)
113        {
114            return 0;
115        }
116    
117        @Deprecated
118        @SideOnly(CLIENT)
119        public static void addAllRenderers(Map<Class<? extends Entity>, Render> renderers)
120        {
121        }
122    
123        @SideOnly(CLIENT)
124        public static void addAnimation(TextureFX anim)
125        {
126            TextureFXManager.instance().addAnimation(anim);
127        }
128    
129        /**
130         * Adds a new prefix to the armor texture list
131         *
132         * {@link RenderingRegistry#addNewArmourRendererPrefix(String)}
133         *
134         * @param armor The new armor prefix
135         * @return The new armor index
136         */
137        @SideOnly(CLIENT)
138        public static int addArmor(String armor)
139        {
140            return RenderingRegistry.addNewArmourRendererPrefix(armor);
141        }
142    
143        /**
144         * This method adds the supplied biome to the set of candidate biomes for the default world generator type.
145         *
146         * @param biome The biome to add
147         */
148        public static void addBiome(BiomeGenBase biome)
149        {
150            GameRegistry.addBiome(biome);
151        }
152    
153        public static void addEntityTracker(BaseMod mod, Class<? extends Entity> entityClass, int entityTypeId, int updateRange, int updateInterval, boolean sendVelocityInfo)
154        {
155            ModLoaderHelper.buildEntityTracker(mod, entityClass, entityTypeId, updateRange, updateInterval, sendVelocityInfo);
156        }
157    
158        public static void addCommand(ICommand command)
159        {
160            ModLoaderHelper.addCommand(command);
161        }
162    
163        /**
164         * Add a behaviour to the dispenser
165         *
166         * @param item
167         * @param behavior
168         */
169        public static void addDispenserBehavior(Item item, IBehaviorDispenseItem behavior)
170        {
171            BlockDispenser.dispenseBehaviorRegistry.putObject(item, behavior);
172        }
173        /**
174         * Add localization for the specified string
175         *
176         * @param key Key
177         * @param value Value
178         */
179        public static void addLocalization(String key, String value)
180        {
181            addLocalization(key, "en_US", value);
182        }
183    
184        /**
185         * Add localization for the specified string
186         *
187         * @param key Key
188         * @param lang Language identifier
189         * @param value Value
190         */
191        public static void addLocalization(String key, String lang, String value)
192        {
193            LanguageRegistry.instance().addStringLocalization(key, lang, value);
194        }
195    
196        /**
197         * Name the specified minecraft object with the supplied name
198         *
199         * @param instance Item to name
200         * @param name The name to give it
201         */
202        public static void addName(Object instance, String name)
203        {
204            addName(instance,"en_US",name);
205        }
206    
207        /**
208         * Unimplemented on the server as it does not generate names
209         *
210         * @param instance Item to name
211         * @param lang Languge identifier
212         * @param name Name to give it
213         */
214        public static void addName(Object instance, String lang, String name)
215        {
216            LanguageRegistry.instance().addNameForObject(instance, lang, name);
217        }
218    
219        /**
220         * Attempts to register a small image to be applied to a larger texture image,
221         * typically how old ModLoader mods add custom Item/Block textures.
222         *
223         * Forge mods should use setTextureFile in Item/Block
224         *
225         * Will return the icon index it was applied to.
226         *
227         * Unimplemented on the server as it does not render textures
228         *
229         * @param fileToOverride The texture to apply the new image to
230         * @param fileToAdd The new image
231         * @return The 'icon index' in the main image that the new image will be applied to
232         */
233        @SideOnly(CLIENT)
234        public static int addOverride(String fileToOverride, String fileToAdd)
235        {
236            return RenderingRegistry.addTextureOverride(fileToOverride, fileToAdd);
237        }
238    
239        /**
240         * Attempts to register a small image to be applied to a larger texture image,
241         * typically how old ModLoader mods add custom Item/Block textures.
242         *
243         * Forge mods should use setTextureFile in Item/Block
244         *
245         * Unimplemented on the server as it does not render textures
246         *
247         * @param path The texture to apply the new image to
248         * @param overlayPath The new image
249         * @param index Where on the texture to apply it
250         */
251        @SideOnly(CLIENT)
252        public static void addOverride(String path, String overlayPath, int index)
253        {
254            RenderingRegistry.addTextureOverride(path, overlayPath, index);
255        }
256    
257        /**
258         * Add a Shaped Recipe
259         *
260         * @param output The result
261         * @param params The input
262         */
263        public static void addRecipe(ItemStack output, Object... params)
264        {
265            GameRegistry.addRecipe(output, params);
266        }
267    
268        /**
269         * Add a shapeless recipe
270         *
271         * @param output The result
272         * @param params The input
273         */
274        public static void addShapelessRecipe(ItemStack output, Object... params)
275        {
276            GameRegistry.addShapelessRecipe(output, params);
277        }
278    
279        /**
280         * Add a new product to be smelted
281         *
282         * @param input
283         * @param output
284         */
285        public static void addSmelting(int input, ItemStack output)
286        {
287            GameRegistry.addSmelting(input, output, 1.0f);
288        }
289    
290        /**
291         * Add a new product to be smelted
292         *
293         * @param input
294         * @param output
295         */
296        public static void addSmelting(int input, ItemStack output, float experience)
297        {
298            GameRegistry.addSmelting(input, output, experience);
299        }
300        /**
301         * Add a mob to the spawn list
302         *
303         * @param entityClass
304         * @param weightedProb
305         * @param min
306         * @param max
307         * @param spawnList
308         */
309        public static void addSpawn(Class<? extends EntityLiving> entityClass, int weightedProb, int min, int max, EnumCreatureType spawnList)
310        {
311            EntityRegistry.addSpawn(entityClass, weightedProb, min, max, spawnList, WorldType.base12Biomes);
312        }
313    
314        /**
315         * Add a mob to the spawn list
316         *
317         * @param entityClass
318         * @param weightedProb
319         * @param min
320         * @param max
321         * @param spawnList
322         * @param biomes
323         */
324        public static void addSpawn(Class<? extends EntityLiving> entityClass, int weightedProb, int min, int max, EnumCreatureType spawnList, BiomeGenBase... biomes)
325        {
326            EntityRegistry.addSpawn(entityClass, weightedProb, min, max, spawnList, biomes);
327        }
328    
329        /**
330         * Add a mob to the spawn list
331         *
332         * @param entityName
333         * @param weightedProb
334         * @param min
335         * @param max
336         * @param spawnList
337         */
338        public static void addSpawn(String entityName, int weightedProb, int min, int max, EnumCreatureType spawnList)
339        {
340            EntityRegistry.addSpawn(entityName, weightedProb, min, max, spawnList, WorldType.base12Biomes);
341        }
342    
343        /**
344         * Add a mob to the spawn list
345         *
346         * @param entityName
347         * @param weightedProb
348         * @param min
349         * @param max
350         * @param spawnList
351         * @param biomes
352         */
353        public static void addSpawn(String entityName, int weightedProb, int min, int max, EnumCreatureType spawnList, BiomeGenBase... biomes)
354        {
355            EntityRegistry.addSpawn(entityName, weightedProb, min, max, spawnList, biomes);
356        }
357    
358        public static void addTrade(int profession, TradeEntry entry)
359        {
360            ModLoaderHelper.registerTrade(profession, entry);
361        }
362        /**
363         * Send a packet from the client
364         * @param packet
365         */
366        public static void clientSendPacket(Packet packet)
367        {
368            PacketDispatcher.sendPacketToServer(packet);
369        }
370    
371        /**
372         * This method is a call in hook from modified external code. Implemented elsewhere.
373         *
374         * @param world
375         * @param x
376         * @param y
377         * @param z
378         * @param xVel
379         * @param zVel
380         * @param item
381         * @return Always false, not implemented here
382         */
383        @Deprecated
384        public static boolean dispenseEntity(World world, double x, double y, double z, int xVel, int zVel, ItemStack item)
385        {
386            return false;
387        }
388    
389        /**
390         * Remove a container and drop all the items in it on the ground around
391         *
392         * @param world
393         * @param x
394         * @param y
395         * @param z
396         */
397        public static void genericContainerRemoval(World world, int x, int y, int z)
398        {
399    /*        TileEntity te = world.func_603_b(x, y, z);
400    
401            if (!(te instanceof IInventory))
402            {
403                return;
404            }
405    
406            IInventory inv = (IInventory)te;
407    
408            for (int l = 0; l < inv.func_469_c(); l++)
409            {
410                ItemStack itemstack = inv.func_468_c(l);
411    
412                if (itemstack == null)
413                {
414                    continue;
415                }
416    
417                float f = world.field_1037_n.nextFloat() * 0.8F + 0.1F;
418                float f1 = world.field_1037_n.nextFloat() * 0.8F + 0.1F;
419                float f2 = world.field_1037_n.nextFloat() * 0.8F + 0.1F;
420    
421                while (itemstack.field_1615_a > 0)
422                {
423                    int i1 = world.field_1037_n.nextInt(21) + 10;
424    
425                    if (i1 > itemstack.field_1615_a)
426                    {
427                        i1 = itemstack.field_1615_a;
428                    }
429    
430                    itemstack.field_1615_a -= i1;
431                    EntityItem entityitem = new EntityItem(world, (float)te.field_823_f + f, (float)te.field_822_g + f1, (float)te.field_821_h + f2, new ItemStack(itemstack.field_1617_c, i1, itemstack.func_21181_i()));
432                    float f3 = 0.05F;
433                    entityitem.field_608_an = (float) world.field_1037_n.nextGaussian() * f3;
434                    entityitem.field_607_ao = (float) world.field_1037_n.nextGaussian() * f3 + 0.2F;
435                    entityitem.field_606_ap = (float) world.field_1037_n.nextGaussian() * f3;
436    
437                    if (itemstack.func_40710_n())
438                    {
439                        entityitem.field_801_a.func_40706_d((NBTTagCompound) itemstack.func_40709_o().func_40195_b());
440                    }
441    
442                    world.func_674_a(entityitem);
443                }
444            }
445    */    }
446    
447        /**
448         * Get a list of all BaseMod loaded into the system
449         * {@link ModLoaderModContainer#findAll}
450         *
451         * @return A list containing all loaded ModLoader mods
452         */
453        public static List<BaseMod> getLoadedMods()
454        {
455            return ModLoaderModContainer.findAll(BaseMod.class);
456        }
457    
458        /**
459         * Get a logger instance {@link FMLCommonHandler#getFMLLogger()}
460         *
461         * @return The current logger
462         */
463        public static Logger getLogger()
464        {
465            return FMLLog.getLogger();
466        }
467    
468        @SideOnly(CLIENT)
469        public static Minecraft getMinecraftInstance()
470        {
471            return FMLClientHandler.instance().getClient();
472        }
473    
474        public static MinecraftServer getMinecraftServerInstance()
475        {
476            return FMLCommonHandler.instance().getMinecraftServerInstance();
477        }
478    
479        /**
480         * Get a value from a field using reflection
481         * {@link ObfuscationReflectionHelper#getPrivateValue(Class, Object, int)}
482         *
483         * @param instanceclass
484         * @param instance
485         * @param fieldindex
486         * @return The value in the specified field.
487         */
488        public static <T, E> T getPrivateValue(Class<? super E> instanceclass, E instance, int fieldindex)
489        {
490            return ObfuscationReflectionHelper.getPrivateValue(instanceclass, instance, fieldindex);
491        }
492    
493        /**
494         * Get a value from a field using reflection
495         * {@link ObfuscationReflectionHelper#getPrivateValue(Class, Object, String[])}
496         *
497         * @param instanceclass
498         * @param instance
499         * @param field
500         * @return The value in the specified field.
501         */
502        public static <T, E> T getPrivateValue(Class<? super E> instanceclass, E instance, String field)
503        {
504            return ObfuscationReflectionHelper.getPrivateValue(instanceclass, instance, field);
505        }
506    
507        /**
508         * Stubbed method on the server to return a unique model id
509         *
510         */
511        @SideOnly(CLIENT)
512        public static int getUniqueBlockModelID(BaseMod mod, boolean inventoryRenderer)
513        {
514            return ModLoaderClientHelper.obtainBlockModelIdFor(mod, inventoryRenderer);
515        }
516    
517        /**
518         * Get a new unique entity id
519         * {@link EntityRegistry#findGlobalUniqueEntityId()}
520         *
521         * @return A unique entity ID
522         */
523        public static int getUniqueEntityId()
524        {
525            return EntityRegistry.findGlobalUniqueEntityId();
526        }
527    
528        @SideOnly(CLIENT)
529        public static int getUniqueSpriteIndex(String path)
530        {
531            return SpriteHelper.getUniqueSpriteIndex(path);
532        }
533    
534        /**
535         * To properly implement packet 250 protocol you should always check your
536         * channel is active prior to sending the packet
537         *
538         * @param player
539         * @param channel
540         * @return If the channel is registered to the current connection.
541         */
542        public static boolean isChannelActive(EntityPlayer player, String channel)
543        {
544            return NetworkRegistry.instance().isChannelActive(channel, (Player)player);
545        }
546    
547        @SideOnly(CLIENT)
548        public static boolean isGUIOpen(Class<? extends GuiScreen> gui)
549        {
550            return FMLClientHandler.instance().getClient().currentScreen != null && FMLClientHandler.instance().getClient().currentScreen.equals(gui);
551        }
552    
553        /**
554         * Is the named mod loaded?
555         * {@link Loader#isModLoaded(String)}
556         *
557         * @param modname
558         * @return If the specified mod is loaded
559         */
560        public static boolean isModLoaded(String modname)
561        {
562            return Loader.isModLoaded(modname);
563        }
564    
565        /**
566         * Implemented elsewhere
567         */
568        @Deprecated
569        public static void loadConfig()
570        {
571        }
572    
573        @SideOnly(CLIENT)
574        public static BufferedImage loadImage(RenderEngine renderEngine, String path) throws Exception
575        {
576            return TextureFXManager.instance().loadImageFromTexturePack(renderEngine, path);
577        }
578    
579        /**
580         * Call in from elsewhere. Unimplemented here.
581         * @param player
582         * @param item
583         */
584        @Deprecated
585        public static void onItemPickup(EntityPlayer player, ItemStack item)
586        {
587        }
588        /**
589         * Call in from elsewhere. Unimplemented here.
590         */
591        @Deprecated
592        @SideOnly(CLIENT)
593        public static void onTick(float tick, Minecraft game)
594        {
595        }
596    
597        @SideOnly(CLIENT)
598        public static void openGUI(EntityPlayer player, GuiScreen gui)
599        {
600            FMLClientHandler.instance().displayGuiScreen(player, gui);
601        }
602    
603        @Deprecated
604        public static void populateChunk(IChunkProvider generator, int chunkX, int chunkZ, World world)
605        {
606        }
607    
608        /**
609         * This method is a call in hook from modified external code. Implemented elsewhere.
610         *
611         * @param packet
612         */
613        @Deprecated
614        public static void receivePacket(Packet250CustomPayload packet)
615        {
616        }
617    
618        @Deprecated
619        @SideOnly(CLIENT)
620        public static KeyBinding[] registerAllKeys(KeyBinding[] keys)
621        {
622            return keys;
623        }
624    
625        @Deprecated
626        @SideOnly(CLIENT)
627        public static void registerAllTextureOverrides(RenderEngine cache)
628        {
629        }
630    
631        /**
632         * Register a new block
633         *
634         * @param block
635         */
636        public static void registerBlock(Block block)
637        {
638            GameRegistry.registerBlock(block);
639        }
640    
641        /**
642         * Register a new block
643         *
644         * @param block
645         * @param itemclass
646         */
647        public static void registerBlock(Block block, Class<? extends ItemBlock> itemclass)
648        {
649            GameRegistry.registerBlock(block, itemclass);
650        }
651    
652        public static void registerContainerID(BaseMod mod, int id)
653        {
654            ModLoaderHelper.buildGuiHelper(mod, id);
655        }
656        /**
657         * Register a new entity ID
658         *
659         * @param entityClass
660         * @param entityName
661         * @param id
662         */
663        public static void registerEntityID(Class<? extends Entity> entityClass, String entityName, int id)
664        {
665            EntityRegistry.registerGlobalEntityID(entityClass, entityName, id);
666        }
667    
668        /**
669         * Register a new entity ID
670         *
671         * @param entityClass
672         * @param entityName
673         * @param id
674         * @param background
675         * @param foreground
676         */
677        public static void registerEntityID(Class<? extends Entity> entityClass, String entityName, int id, int background, int foreground)
678        {
679            EntityRegistry.registerGlobalEntityID(entityClass, entityName, id, background, foreground);
680        }
681    
682        @SideOnly(CLIENT)
683        public static void registerKey(BaseMod mod, KeyBinding keyHandler, boolean allowRepeat)
684        {
685            ModLoaderClientHelper.registerKeyBinding(mod, keyHandler, allowRepeat);
686        }
687    
688        /**
689         * Register the mod for packets on this channel.
690         * {@link NetworkRegistry#registerChannel(IPacketHandler, String)}
691         *
692         * @param mod
693         * @param channel
694         */
695        public static void registerPacketChannel(BaseMod mod, String channel)
696        {
697            NetworkRegistry.instance().registerChannel(ModLoaderHelper.buildPacketHandlerFor(mod), channel);
698        }
699    
700        /**
701         * Register a new tile entity class
702         *
703         * @param tileEntityClass
704         * @param id
705         */
706        public static void registerTileEntity(Class<? extends TileEntity> tileEntityClass, String id)
707        {
708            GameRegistry.registerTileEntity(tileEntityClass, id);
709        }
710    
711        @SideOnly(CLIENT)
712        public static void registerTileEntity(Class<? extends TileEntity> tileEntityClass, String id, TileEntitySpecialRenderer renderer)
713        {
714            ClientRegistry.registerTileEntity(tileEntityClass, id, renderer);
715        }
716    
717        /**
718         * Remove a biome from the list of generated biomes
719         *
720         * @param biome
721         */
722        public static void removeBiome(BiomeGenBase biome)
723        {
724            GameRegistry.removeBiome(biome);
725        }
726    
727        /**
728         * Remove a spawn
729         *
730         * @param entityClass
731         * @param spawnList
732         */
733        public static void removeSpawn(Class<? extends EntityLiving> entityClass, EnumCreatureType spawnList)
734        {
735            EntityRegistry.removeSpawn(entityClass, spawnList, WorldType.base12Biomes);
736        }
737    
738        /**
739         * Remove a spawn
740         *
741         * @param entityClass
742         * @param spawnList
743         * @param biomes
744         */
745        public static void removeSpawn(Class<? extends EntityLiving> entityClass, EnumCreatureType spawnList, BiomeGenBase... biomes)
746        {
747            EntityRegistry.removeSpawn(entityClass, spawnList, biomes);
748        }
749    
750        /**
751         * Remove a spawn
752         *
753         * @param entityName
754         * @param spawnList
755         */
756        public static void removeSpawn(String entityName, EnumCreatureType spawnList)
757        {
758            EntityRegistry.removeSpawn(entityName, spawnList, WorldType.base12Biomes);
759        }
760    
761        /**
762         * Remove a spawn
763         *
764         * @param entityName
765         * @param spawnList
766         * @param biomes
767         */
768        public static void removeSpawn(String entityName, EnumCreatureType spawnList, BiomeGenBase... biomes)
769        {
770            EntityRegistry.removeSpawn(entityName, spawnList, biomes);
771        }
772    
773        @Deprecated
774        @SideOnly(CLIENT)
775        public static boolean renderBlockIsItemFull3D(int modelID)
776        {
777            return RenderingRegistry.instance().renderItemAsFull3DBlock(modelID);
778        }
779    
780        @Deprecated
781        @SideOnly(CLIENT)
782        public static void renderInvBlock(RenderBlocks renderer, Block block, int metadata, int modelID)
783        {
784            RenderingRegistry.instance().renderInventoryBlock(renderer, block, metadata, modelID);
785        }
786    
787        @Deprecated
788        @SideOnly(CLIENT)
789        public static boolean renderWorldBlock(RenderBlocks renderer, IBlockAccess world, int x, int y, int z, Block block, int modelID)
790        {
791            return RenderingRegistry.instance().renderWorldBlock(renderer, world, x, y, z, block, modelID);
792        }
793    
794        /**
795         * Configuration is handled elsewhere
796         * {@link ModLoaderModContainer}
797         */
798        @Deprecated
799        public static void saveConfig()
800        {
801        }
802    
803        /**
804         * Send a packet from client to server
805         *
806         * @param packet
807         */
808        public static void sendPacket(Packet packet) {
809            PacketDispatcher.sendPacketToServer(packet);
810        }
811        /**
812         * Send a chat message to the server
813         *
814         * @param text
815         */
816        @Deprecated
817        public static void serverChat(String text)
818        {
819            //TODO
820        }
821    
822        @Deprecated
823        @SideOnly(CLIENT)
824        public static void serverLogin(NetClientHandler handler, Packet1Login loginPacket)
825        {
826            //TODO
827        }
828    
829        public static void serverSendPacket(NetServerHandler handler, Packet packet)
830        {
831            if (handler != null)
832            {
833                PacketDispatcher.sendPacketToPlayer(packet, (Player)handler.getPlayer());
834            }
835        }
836        public static void serverOpenWindow(EntityPlayerMP player, Container container, int ID, int x, int y, int z)
837        {
838            ModLoaderHelper.openGui(ID, player, container, x, y, z);
839        }
840    
841        /**
842         * Indicate that you want to receive ticks
843         *
844         * @param mod receiving the events
845         * @param enable indicates whether you want to recieve them or not
846         * @param useClock don't receive render subticks, just world ticks
847         */
848        public static void setInGameHook(BaseMod mod, boolean enable, boolean useClock)
849        {
850            ModLoaderHelper.updateStandardTicks(mod, enable, useClock);
851        }
852    
853    
854        public static void setInGUIHook(BaseMod mod, boolean enable, boolean useClock)
855        {
856            ModLoaderHelper.updateGUITicks(mod, enable, useClock);
857        }
858    
859        /**
860         * Set a private field to a value using reflection
861         * {@link ObfuscationReflectionHelper#setPrivateValue(Class, Object, int, Object)}
862         *
863         * @param instanceclass
864         * @param instance
865         * @param fieldindex
866         * @param value
867         */
868        public static <T, E> void setPrivateValue(Class<? super T> instanceclass, T instance, int fieldindex, E value)
869        {
870            ObfuscationReflectionHelper.setPrivateValue(instanceclass, instance, value, fieldindex);
871        }
872    
873        /**
874         * Set a private field to a value using reflection
875         * {@link ObfuscationReflectionHelper#setPrivateValue(Class, Object, String, Object)}
876         *
877         * @param instanceclass
878         * @param instance
879         * @param field
880         * @param value
881         */
882        public static <T, E> void setPrivateValue(Class<? super T> instanceclass, T instance, String field, E value)
883        {
884            ObfuscationReflectionHelper.setPrivateValue(instanceclass, instance, value, field);
885        }
886    
887        /**
888         * This method is a call in hook from modified external code. Implemented elsewhere.
889         *
890         * @param player
891         * @param item
892         * @param matrix
893         */
894        @Deprecated
895        public static void takenFromCrafting(EntityPlayer player, ItemStack item, IInventory matrix)
896        {
897        }
898    
899        /**
900         * This method is a call in hook from modified external code. Implemented elsewhere.
901         *
902         * @param player
903         * @param item
904         */
905        @Deprecated
906        public static void takenFromFurnace(EntityPlayer player, ItemStack item)
907        {
908        }
909    
910        /**
911         * Throw the offered exception. Likely will stop the game.
912         *
913         * @param message
914         * @param e
915         */
916        public static void throwException(String message, Throwable e)
917        {
918            FMLCommonHandler.instance().raiseException(e, message, true);
919        }
920    
921        public static void throwException(Throwable e)
922        {
923            throwException("Exception in ModLoader", e);
924        }
925    }