Naming subblocks of any metablock with a single class?

Asked

Viewed 34 times

1

I am trying to make only one class necessary to name the subblocks of any metablock that uses this class at the time of the record, ie naming them as if they were parameter values, but without using a.

Although this revolves around an API (Minecraft Forge), I think the problem is more Java, so I make here a brief explanation of how it works what I intend to do.

A metablock is composed of subblocks, which are variations of the same block (for example, the same block, but which only changes the texture and name). Each subblock needs a name to identify it. These names are listed in the class ExemploItemBlock in a String[], and then are named in the format nomeDoMetablock.nomeDoSubBlock (ex.: ExemploMetablock.azul, ExemploMetablock.verde, etc.), with

// Classe ExemploItemBlock

public static final String[] SUBNAMES = new String[] {"azul", "verde", "amarelo"};

@Override
public String getUnlocalizedName(ItemStack itemStack) 
{
    int i = itemStack.getItemDamage();
    return getUnlocalizedName() + "." + SUBNAMES[i];
}

Then the metablock ExemploMetaBlock is instantiated and recorded with

// Classe onde são feitos os registros   

public static Block ExemploMetaBlock = new ExemploMetaBlock(); 

GameRegistry.registerBlock(ExemploMetaBlock, ExemploItemBlock.class, "ExemploMetaBlock");

After that, everything works smoothly, however I would have to create an Itemblock class for every new metablock I want to do, and I don’t think this is very practical or appropriate, finding it best to create a single class to be used by any future metablock.

As you can see, the second parameter of the method GameRegistry.registerBlock() (which is an API method) requires a value of type Class. And that’s the problem: how I’m going to make class ExemploItemBlock dynamics without using instances?

I even tried to add a String[] parameter to the ExemploItemBlock and use an instance with the names in place of the class name, but as expected, accused incompatibility of types, as it is just Class the accepted type.

I looked everywhere for a way to do this, but only found two ways:

1. create an Itemblock class for each new metablock;
2. trade in SUBNAMES[i] in the getUnlocalizedName() for i or itemStack.getItemDamage() naming subblocks by numbers instead of names (eg.: ExemploMetaBlock.0, ExemploMetaBlock.1, etc.), without using String[] or anything and becoming a universal class. But this way is also very antipratic, because then it makes it very difficult to identify which subblock is which.

So my question is: is there any way to get a universal Itemblock class, but name subblocks by names (words)?

Content of classes: Exemplometablock, Exemploitemblock.

1 answer

1


I ended up finding the solution in Forge itself, as it can be accompanied here.

But for the sake of information, I’ll give you an explanation about the solution.


I didn’t know, but the method GameRegistry.registerBlock() also accepts a fourth parameter of type Object[]. Then just put the list with the names inside the Object[], only start variable String[] of ExemploMetablock, and pass the values defined in the Object[] parameter to the variable String[]. Thus remaining:

public static String[] SUBNAMES;
private IIcon[] icon;

public ExemploMetaBlock(Material material, String name, CreativeTabs tab, String[] subnames)
{
    super(material, name, tab);
    SUBNAMES = subnames;
}

And instead of using class ExemploItemBlock, a separate class created in the parameter Class, I recommend that you use instead a class that already exists in Minecraft’s own code and that does practically the same thing as the ExemploItemBlock, which is the class ItemMultiTexture (If you have nothing else ItemMultiTexture). Getting the record like this:

public static final String[] SubNames = new String[] {"azul", "verde", "amarelo", "vermelho"}; 
public static Block ExemploMetablock = new ExemploMetablock(Material.rock, "ExemploMetablock", Tabs.ExemploModTab, SubNames); 

GameRegistry.registerBlock(ExemploMetablock, ItemMultiTexture.class, "ExemploMetablock", new Object[]{SubNames});

However, this will not compile. Error will occur NoSuchMethodException on the record line (GameRegistry.registerBlock ....).

The builder of the class ItemMultiTexture takes the values defined in the method parameters registerBlock() which correspond with the types of the parameters of your constructor, which are Block, Block, String[].

Was informed a String[]? Yes. A Block? Yes. You were informed a second ago Block? No. "There is no such method", there is no constructor of ItemMultiTexture with parameters Block, String[].

This is because, as has been said, the class builder ItemMultiTexture requires two values Block.

To solve this, simply create a new class (or replace the ExemploItemBlock) extending ItemMultiTexture and that super both Blocks in the parameter. Thus:

public class ItemMultiTextureHelper extends ItemMultiTexture
{
    public ItemMultiTextureHelper(Block block, String[] names)
    {
        super(block, block, names);
    }
}

And the registerBlock() thus:

GameRegistry.registerBlock(ExemploMetablock, ItemMultiTextureHelper.class, "ExemploMetablock", new Object[]{SubNames});

And one last thing, but not least: remove the modifier static of SUBNAMES, otherwise this will cause the biggest mess in future metablocks, for example, all sub-Blocks of metablocks being named with the names of the first metablock created, sub-Blocks repeated, etc. (I went through these problems right now, and fixed by removing the static.) So the right thing is actually like this:

public String[] SUBNAMES;

Browser other questions tagged

You are not signed in. Login or sign up in order to post.