Créer un item générateur de structure



  • Sommaire

    Introduction

    Salut à tous, dans ce tutoriel je vais vous apprendre à créer un item qui, à l'aide d'un clique droit, va faire apparaitre une structure.
    Pour ce qui est de la structure en elle même, je vous réfère au tutoriel sur les structure d' AlphaSwittleTeam.

    Pré-requis

    Code

    Les items

    Tout d'abord rajoutez ceci dans la fonction preInit de votre classe principale:

        //Déclaration des items
        public static Item gen_totem1;
        public static Item gen_totem2;
    
        //Initialisation
        gen_totem1 = new ItemStructureGen(1).setUnlocalizedName("gen_totem1").setTextureName(Reference.MOD_ID + ":gen_totem1"); 
        gen_totem2 = new ItemStructureGen(2).setUnlocalizedName("gen_totem2").setTextureName(Reference.MOD_ID + ":gen_totem2");
    
        //Enregistrements
        GameRegistry.registerItem(gen_totem1, "gen_totem1");
        GameRegistry.registerItem(gen_totem2, "gen_totem2");
    

    Ici, vous avez une erreur sur la classe ItemStructureGen, créez-là.

    La classe ItemStructureGen

    Une fois votre classe créée,

    extends Item
    

    Créez son constructeur comme ceci:

        public ItemStructureGen(int struct) //Reçoit en argument la  structure(totem1, totem2, ...)
        {
            this.structure = struct; //Enregistrement de la valeur reçue dans la variable structure
        }
    
        //N'oubliez pas de rajouter ceci juste après le { de la classe:
        public final int structure;
    

    Maintenant, rajoutez cette fonction:

        public boolean onItemUse(ItemStack itemStack, EntityPlayer player, World world, int x, int y, int z, int side, float hitX, float hitY, float hitZ)
        {
    
        }
    

    Elle va permettre de dire quoi faire quand on fait un clique droit avec l'item en main

    Rajoutez ce code dedans:

            switch(structure) 
            {
                case 1:
                    StructureTotem1.generate(world, x, y+1, z); //Ici, on fait y+1 de manière à ce que quand on fait un clique sur le sol la structure se génère sur le sol et pas dedans
                    return true;
    
                case 2:
                    StructureTotem2.generate(world, x, y+1, z);
                    return true;
    
                default:
                    return false;
            }
    

    Donc, on switch la variable structure, si elle est égale à 1, on génère le Totem1 et si elle est égale à 2, on génère le Totem2.
    Ce qui est bien avec cette technique c'est qu'on a très facile pour rajouter d'autres structures.

    La classe ItemStructureGen doit ressembler à ça:

    public class ItemStructureGen extends Item
    {
        public final int structure;
    
        public ItemStructureGen(int struct)
        {
            this.structure = struct;
        }
    
        public boolean onItemUse(ItemStack itemStack, EntityPlayer player, World world, int x, int y, int z, int side, float hitX, float hitY, float hitZ)
        {
            switch(structure)
            {
                case 1:
                    StructureTotem1.generate(world, x, y+1, z);
                    return true;
    
                case 2:
                    StructureTotem2.generate(world, x, y+1, z);
                    return true;
    
                default:
                    return false;
            }
        }
    }
    

    Les 2 classes si-dessus ne sont pas encore créés, faites-le.

    Les structures :

    Pour ma part, je vais créer ces 2 totems:
    1466261783-totem-1.jpg
    1466261783-totem-2.jpg

    Ajoutez cette fonction:

    public static boolean generate(World world, int x, int y, int z)
    {
    
    }
    

    Ensuite, ajoutez ceci:

        //netherrack
        world.setBlock(x-1, y, z, Blocks.netherrack);
        world.setBlock(x+1, y, z, Blocks.netherrack);
        world.setBlock(x-1, y+2, z, Blocks.netherrack);
        world.setBlock(x+1, y+2, z, Blocks.netherrack);
        world.setBlock(x, y+1, z, Blocks.netherrack);
    
        //quartz
        world.setBlock(x, y, z, Blocks.quartz_block);
        world.setBlock(x, y+2, z, Blocks.quartz_block);
    
        return true;
    

    Encore une fois, allez voir le tutoriel d'AlphaSwittleTeam pour comprendre.

    La classe StructureTotem1 finie:

    public class StructureTotem1
    {
        public static boolean generate(World world, int x, int y, int z)
        {
            //netherrack
            world.setBlock(x-1, y, z, Blocks.netherrack);
            world.setBlock(x+1, y, z, Blocks.netherrack);
            world.setBlock(x-1, y+2, z, Blocks.netherrack);
            world.setBlock(x+1, y+2, z, Blocks.netherrack);
            world.setBlock(x, y+1, z, Blocks.netherrack);
    
            //quartz
            world.setBlock(x, y, z, Blocks.quartz_block);
            world.setBlock(x, y+2, z, Blocks.quartz_block);
    
            return true;
        }
    }
    

    Et ma classe StructureTotem2:

    public class StructureTotem2
    {
        public static boolean generate(World world, int x, int y, int z)
        {
            //lapis-lazuli
            world.setBlock(x-1, y, z, Blocks.lapis_block);
            world.setBlock(x+1, y, z, Blocks.lapis_block);
            world.setBlock(x-1, y+2, z, Blocks.lapis_block);
            world.setBlock(x+1, y+2, z, Blocks.lapis_block);
            world.setBlock(x, y+1, z, Blocks.lapis_block);
    
            //dirt
            world.setBlock(x, y+2, z, Blocks.dirt);
            world.setBlock(x, y+3, z, Blocks.dirt);
    
            return true;
        }
    }
    

    Bonus

    Supprimer son item après utilisation :

    Vous pourriez trouver cela un peu cheaté de pouvoir faire apparaître des structures à l'infini avec le même item.
    Voilà comment y remédier.

    Tout d'abord rajouter en dessous de StructureTotem1.generate(...) et StructureTotem2.generate(...) ceci:

    use(itemStack, player);
    

    Créez cette méthode comme ceci:

        private void use(ItemStack itemStack, EntityPlayer player)
        {
            if (!player.capabilities.isCreativeMode) //Si le joueur n'est pas en créatif
            {
                --itemStack.stackSize; //Décrémentation du stack, suppression de l'item
            }
        }
    

    Votre classe finie doit ressembler à ça:

    public class ItemStructureGen extends Item
    {
        public final int structure;
    
        public ItemStructureGen(int struct)
        {
            this.structure = struct;
        }
    
        public boolean onItemUse(ItemStack itemStack, EntityPlayer player, World world, int x, int y, int z, int side, float hitX, float hitY, float hitZ)
        {
            switch(structure)
            {
                case 1:
                    StructureTotem1.generate(world, x, y+1, z);
                    use(itemStack, player);
                    return true;
    
                case 2:
                    StructureTotem2.generate(world, x, y+1, z);
                    use(itemStack, player);
                    return true;
    
                default:
                    return false;
            }
        }
    
        private void use(ItemStack itemStack, EntityPlayer player)
        {
            if (!player.capabilities.isCreativeMode)
            {
                --itemStack.stackSize;
            }
        }
    }
    

    Résultats

    1466264136-totem1.gif
    1466264136-totem2.gif

    Crédits

    Rédaction :

    • Minantcraft

    Correction :


    Ce tutoriel de Minecraft Forge France est mis à disposition selon les termes de la licence Creative Commons Attribution - Pas d’Utilisation Commerciale - Partage dans les Mêmes Conditions 4.0 International

    Retour vers le sommaire des tutoriels


  • Rédacteurs

    Pour le random tu peux utiliser celui de la variable world, et extends ta classe de génération worldGenerator ne sert à rien, de toute façon tu ne l'enregistre pas comme tel



  • Bonjour alors déjà, bon tutoriel bien expliqué et sans aucune faute, j'ai une petite modification à proposer, tu pourrais remplacer le

    Random rand = new Random();
    

    dans la fonction onItemUse par

    Random rand = world.rand
    

    ce qui permettrait d'avoir un Random en fonction de la seed du monde 🙂
    EDIT : et aussi adapter le tuto pour la 1.8/1.9, le seul truc qui change, c'est x,y,z remplacé par BlockPos.



  • @'AymericRed':

    Bonjour alors déjà, bon tutoriel bien expliqué et sans aucune faute, j'ai une petite modification à proposer, tu pourrais remplacer le

    Random rand = new Random();
    

    dans la fonction onItemUse par

    Random rand = world.rand
    

    ce qui permettrait d'avoir un Random en fonction de la seed du monde 🙂

    Ok je modifie ça.


  • Rédacteurs

    Et à un moment tu dis, "ça vous a créé un constructeur assez dégueulasse", mais c'est pas un constructeur, c'est juste une fonction avec des paramètres



  • @'BrokenSwing':

    Et à un moment tu dis, "ça vous a créé un constructeur assez dégueulasse", mais c'est pas un constructeur, c'est juste une fonction avec des paramètres

    Oui je sais j'ai changé et j'ai aussi enlevé le extends WorldGenerator et le random

    EDIT: J'ai changé "Ajoutez ce constructeur" par "Ajoutez cette fonction"


  • Rédacteurs

    Et un truc de + (désolé xD) mais tu pourrai rendre ta fonction generate(World, int, int, int) static parce que tu n'as aucune utilitée à créer une instance de la classe



  • @'BrokenSwing':

    Et un truc de + (désolé xD) mais tu pourrai rendre ta fonction generate(World, int, int, int) static parce que tu n'as aucune utilitée à créer une instance de la classe

    C'est fait!


  • Rédacteurs

    Mais du coup la fonction dans l'item devient :

    public boolean onItemUse(ItemStack itemStack, EntityPlayer player, World world, int x, int y, int z, int side, float hitX, float hitY, float hitZ)
    {
        switch(structure)
        {
        case 1:
            StructureTotem1.generate(world, x, y+1, z);
            return true;
        case 2:
            StructureTotem2.generate(world, x, y+1, z);
            return true;
        default:
            return false;
        }
    }
    


  • OK.



  • Tutoriel pas trop mal dans l'ensemble même si un peu plus de précisions sur où placer certaines parties de code n'auraient pas étaient de trop.

    PS : ce serait bien de rajouter le fait que l'item se détruise une fois utilisé sinon ça me paraît un peu cheaté à utiliser.



  • @'SCAREX':

    Tutoriel pas trop mal dans l'ensemble même si un peu plus de précisions sur où placer certaines parties de code n'auraient pas étaient de trop.

    PS : ce serait bien de rajouter le fait que l'item se détruise une fois utilisé sinon ça me paraît un peu cheaté à utiliser.

    C'est pour ça que je met à chaque fin de partie la classe en entière.

    PS: Ça pourrait être un item réservé au créatif qui permet d'avoir la structure sans devoir cherché dans le monde mais je vais voir pour la destruction de l'item dans la partie bonus



  • Un simple if (player.isInCreativeMode()) player.getEquippedItem().stacksize–; est suffisant (pas totalement sûr du code)



  • Tuto fini, avec BONUS.


Log in to reply