1.7.10の開発講座を修正中です。このページには誤りや古い情報が含まれる可能性があります。
特殊な形のブロックを追加する。
今回は、アルミ製の金床を追加する。
(……としたいのだが、金床のGUIに関しては、実装していない。悪しからず。)
この内容はとても難解なものを含んでいるうえ、汎用性に乏しい。
そのため、更に汎用性の高いものを作る場合は、net.minecraft.client.rendererのRenderBlocksを参照。
目次
ソースコード
package aluminiummod.common;
import net.minecraft.block.Block;
import net.minecraft.creativetab.CreativeTabs;
import cpw.mods.fml.client.registry.RenderingRegistry;
import cpw.mods.fml.common.FMLCommonHandler;
import cpw.mods.fml.common.Mod;
import cpw.mods.fml.common.Mod.EventHandler;
import cpw.mods.fml.common.event.FMLInitializationEvent;
import cpw.mods.fml.common.event.FMLPreInitializationEvent;
import cpw.mods.fml.common.registry.GameRegistry;
import cpw.mods.fml.relauncher.Side;
/**
*
* @author Akasata Nahama & Tom Kate & YOU!!
*
*/
@Mod(modid = "AluminiumMod", name = "Aluminium Mod")
public class AluminiumMod {
//追加するブロックの定義
/*public static Block * ;*/
public static Block AnvilAluminium;
//レンダーIDの取得
public static int RenderID;
@EventHandler
public void perInit(FMLPreInitializationEvent event) {
/*ブロックの実装。詳細割愛。*/
AnvilAluminium = new AnvilAluminium();
AnvilAluminium.setCreativeTab(CreativeTabs.tabBlock);
AnvilAluminium.setBlockName("blockAluminium");
AnvilAluminium.setBlockTextureName("aluminiummod:aluminium_anvil");
GameRegistry.registerBlock(AnvilAluminium, "AnvilAluminium");
}
@EventHandler
public void init (FMLInitializationEvent event) {
/*FMLCommonHandler.instance().getSide() で、クライアントサイドでのみの動作としている。*/
if(FMLCommonHandler.instance().getSide() == Side.CLIENT)
{
/*レンダーIDの設定。
* RenderingRegistry.getNextAvailableRenderId() で、未使用のレンダーIDを取得する。*/
this.RenderID = RenderingRegistry.getNextAvailableRenderId();
/*ブロックのレンダラ―を設定する。
*RenderingRegistry.registerBlockHandler(ISimpleBlockRenderingHandler); */
RenderingRegistry.registerBlockHandler(new RenderAnvilAluminium());
}
}
package aluminiummod.common;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.world.IBlockAccess;
import cpw.mods.fml.relauncher.Side;
import cpw.mods.fml.relauncher.SideOnly;
public class AnvilAluminium extends Block{
public AnvilAluminium() {
super(Material.rock);
}
/**レンダーIDを返す。**/
@Override
public int getRenderType()
{
return AluminiumMod.RenderID;
}
/**ブロックが透けるか否かを返す。**/
@SideOnly(Side.CLIENT)
public boolean shouldSideBeRendered(IBlockAccess p_149646_1_, int p_149646_2_, int p_149646_3_, int p_149646_4_, int p_149646_5_)
{
return true;
}
/**通常のブロックでないかを返す。*/
public boolean renderAsNormalBlock()
{
return false;
}
/**ブロックが透明か否かを返す。*/
public boolean isOpaqueCube()
{
return false;
}
}
package aluminiummod.common;
import net.minecraft.block.Block;
import net.minecraft.client.renderer.RenderBlocks;
import net.minecraft.client.renderer.Tessellator;
import net.minecraft.world.IBlockAccess;
import org.lwjgl.opengl.GL11;
import cpw.mods.fml.client.registry.ISimpleBlockRenderingHandler;
public class RenderAnvilAluminium implements ISimpleBlockRenderingHandler
{
/**インベントリ内でブロックをレンダリングするメソッド。もしshouldRender3DInInventoryがfalseなら空でもいいかも。**/
@Override
public void renderInventoryBlock(Block block, int metadata, int modelId, RenderBlocks renderer)
{
if (modelId == this.getRenderId())
{
float f = 0;
f = this.renderAlumiAnvil(block, renderer, metadata, f, 0.75F, 0.25F, 0.75F ,false);
f = this.renderAlumiAnvil(block, renderer, metadata, f, 0.5F, 0.0625F, 0.625F ,false);
f = this.renderAlumiAnvil(block, renderer, metadata, f, 0.25F, 0.3125F, 0.5F ,false);
this.renderAlumiAnvil(block, renderer, metadata, f, 0.625F, 0.375F, 1.0F ,false);
}
}
/**ワールド内でブロックをレンダリングするメソッド**/
@Override
public boolean renderWorldBlock(IBlockAccess world, int x, int y, int z, Block block, int modelId, RenderBlocks renderer)
{
if (modelId == this.getRenderId())
{
/*レンダリングする立方体のサイズを決めるメソッド。
* setRenderBounds(始点X, 始点Y, 始点Z, 終点X, 終点Y, 終点Z)*/
renderer.setRenderBounds(0.1D, 0.0D, 0.1D, 0.9D, 0.2D, 0.9D);
/*レンダリングするメソッド。
* renderStandardBlock(block, x, y, z);*/
renderer.renderStandardBlock(block, x, y, z);
renderer.setRenderBounds(0.25D, 0.2D, 0.25D, 0.75D, 0.3D, 0.75D);
renderer.renderStandardBlock(block, x, y, z);
renderer.setRenderBounds(0.3D, 0.3D, 0.2D, 0.7D, 0.6D, 0.8D);
renderer.renderStandardBlock(block, x, y, z);
renderer.setRenderBounds(0.2D, 0.6D, 0.0D, 0.8D, 1.0D, 1.0D);
renderer.renderStandardBlock(block, x, y, z);
return true;
}
return false;
}
@Override
/**インベントリ内で3Dレンダリングするか否かを返すメソッド**/
public boolean shouldRender3DInInventory(int modelId) {
return true;
}
/**自身のレンダーIDを返すメソッド**/
@Override
public int getRenderId() {
return AluminiumMod.RenderID;
}
protected float renderAlumiAnvil(Block block , RenderBlocks renderer , int metadata , float sides1 , float sides2 , float sides3 , float sides4 , boolean flg)
{
/**詳しい説明はカット。ここは難しいため、基本的にはshouldRender3DInInventoryをfalseにすることをお勧めする。**/
if(flg)
{
float f = sides2;
sides2 = sides4;
sides4 =f;
}
sides2 /= 2.0F;
sides4 /= 2.0F;
renderer.setRenderBounds((double)(0.5F - sides2), (double)sides1, (double)(0.5F - sides4), (double)(0.5F + sides2), (double)(sides1 + sides3), (double)(0.5F + sides4));
/*これより下は、ブロックを各面ごとにレンダリングしている。*/
Tessellator tessellator = Tessellator.instance;
GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
tessellator.startDrawingQuads();
tessellator.setNormal(0.0F, -1.0F, 0.0F);
renderer.renderFaceYNeg(block, 0.0D, 0.0D, 0.0D, renderer.getBlockIconFromSideAndMetadata(block, 0, metadata));
tessellator.draw();
tessellator.startDrawingQuads();
tessellator.setNormal(0.0F, 1.0F, 0.0F);
renderer.renderFaceYPos(block, 0.0D, 0.0D, 0.0D, renderer.getBlockIconFromSideAndMetadata(block, 1, metadata));
tessellator.draw();
tessellator.startDrawingQuads();
tessellator.setNormal(0.0F, 0.0F, -1.0F);
renderer.renderFaceZNeg(block, 0.0D, 0.0D, 0.0D, renderer.getBlockIconFromSideAndMetadata(block, 2, metadata));
tessellator.draw();
tessellator.startDrawingQuads();
tessellator.setNormal(0.0F, 0.0F, 1.0F);
renderer.renderFaceZPos(block, 0.0D, 0.0D, 0.0D, renderer.getBlockIconFromSideAndMetadata(block, 3, metadata));
tessellator.draw();
tessellator.startDrawingQuads();
tessellator.setNormal(-1.0F, 0.0F, 0.0F);
renderer.renderFaceXNeg(block, 0.0D, 0.0D, 0.0D, renderer.getBlockIconFromSideAndMetadata(block, 4, metadata));
tessellator.draw();
tessellator.startDrawingQuads();
tessellator.setNormal(1.0F, 0.0F, 0.0F);
renderer.renderFaceXPos(block, 0.0D, 0.0D, 0.0D, renderer.getBlockIconFromSideAndMetadata(block, 5, metadata));
tessellator.draw();
GL11.glTranslatef(0.5F, 0.5F, 0.5F);
renderer.setRenderBounds(0.0D, 0.0D, 0.0D, 1.0D, 1.0D, 1.0D);
return sides1 + sides3;
}
}
解説
RenderAnvilAluminium
この中では、インベントリ内でのレンダリングが一番難しいはずである。
もし大変ならば、shouldRender3DInInventoryをfalseにすればインベントリにはテクスチャのみが表示されるため、作業が楽になる。
クラッシュレポートをtomkate☆tntmodders.com (☆を@に変えてください)に送っていただけますでしょうか。
よろしくおねがいします。
マルチで使用するとクラッシュするのですが