Posted June 14, 201411 yr Hi! I want to rotate the textures of some block faces based of the orientation of the block. The problem is, I don't want to setup a texture for every possible state, that would be too much I know I can achieve this with using an ISimpleBlockRenderingHandler and registering it with my custom block. But I can't really figure out how to properly write the public boolean renderWorldBlock(IBlockAccess world, int x, int y, int z, Block block, int modelId, RenderBlocks renderer) { } method in my custom rendering class. More details of what I want to achieve: The TileEntity can already face in any of the six minecraft directions. Based on its orientation the textures that are not "front" and "back" have to be rotated properly because of their visuals. I searched a bit here and there but I did not find a source I could work with. Maybe I did not understand something the right way. The problem is, I don't really know how to setup the renderWorldBlock method. Only thing that I think I am knowing is that I have to use the "uveRotate*" methods of the RenderBlocks class.. Regards, Jhary
June 14, 201411 yr That could work. Not really sure what that is though. This question is making me think tessellator. With it you can render a basic cube and depending on the state, start at different points and draw the same texture. Viola, textures rotated. But yeah... That could be inefficient. We all stuff up sometimes... But I seem to be at the bottom of that pot.
June 14, 201411 yr Hi These links might be helpful http://greyminecraftcoder.blogspot.com.au/2013/07/rendering-standard-blocks-cubes.html and http://greyminecraftcoder.blogspot.com.au/2013/07/rendering-non-standard-blocks.html and http://greyminecraftcoder.blogspot.com.au/2013/08/the-tessellator.html -TGG
June 14, 201411 yr Author Thanks for the links. I will study the content and try to get it working. I will post again after I tried everything out
June 14, 201411 yr Author Hmm ok I can't really wrap my head around this tessellator stuff, but it seems to be exactly what I need. Sadly I can't find a good example of someone using this with 1.7. I understand how to first setup the tessellator and that I have to do for each side of a block 4 times the "addVertexWithUV(x, y, z, u, v)" method. But I don't really understand how to setup the parameters. Lets say my block has the in world coordinates [10 ; 10 ; 10]. How would I setup the first four addVertexWithUV calls, lets say for the south side? In this article (http://greyminecraftcoder.blogspot.com.au/2013/08/the-tessellator.html) there are four points defined as A, B, C and D I would understand this as follows according to the picture in the article : A: .addVertexWithUV(11, 10, 10, u, v) B: .addVertexWithUV(11, 11, 10, u, v) C: .addVertexWithUV(10, 11, 10, u, v) D: .addVertexWithUV(10, 10, 10, u, v) Would here x, y, z be correct? And if yes, how would I now find out what I have to use for u and v ?
June 14, 201411 yr Hi If you are doing the z = 10 positive face (south), then yes that's right, except that in an IBSRH it has already translated the coordinates for you, so you should draw between [0,0,0] and [1,1,1] instead, i.e. A: .addVertexWithUV(1, 0, 0, u, v) B: .addVertexWithUV(1, 1, 0, u, v) etc regarding u,v: if you have bound the texture yourself and the face is the whole texture, then your u,v coordinates are 0 -> 1 with the v axis pointing in the opposite direction to y, so in your case A: .addVertexWithUV(1, 0, 0, 1, 1) B: .addVertexWithUV(1, 1, 0, 1, 0) etc If each of your faces is an icon (the usual way to do it), use icon.getMinU(), icon.getMaxU(), icon.getMinV(), icon.getMaxV() -TGG
June 14, 201411 yr Author ok I got it now working that it renders correctly. Here is my method so far: @Override public boolean renderWorldBlock(IBlockAccess world, int x, int y, int z, Block block, int modelId, RenderBlocks renderer) { Tessellator tessellator = Tessellator.instance; IIcon up = block.getIcon(world, x, y, z, 1); IIcon down = block.getIcon(world, x, y, z, 0); IIcon north = block.getIcon(world, x, y, z, 2); IIcon south = block.getIcon(world, x, y, z, 3); IIcon west = block.getIcon(world, x, y, z, 4); IIcon east = block.getIcon(world, x, y, z, 5); //Down 0 tessellator.addVertexWithUV(x+1, y , z , (double)down.getMaxU(), (double)down.getMaxV()); tessellator.addVertexWithUV(x+1, y , z+1, (double)down.getMaxU(), (double)down.getMinV()); tessellator.addVertexWithUV(x , y , z+1, (double)down.getMinU(), (double)down.getMinV()); tessellator.addVertexWithUV(x , y , z , (double)down.getMinU(), (double)down.getMaxV()); //Up 1 tessellator.addVertexWithUV(x+1, y+1, z+1, (double)up.getMaxU(), (double)up.getMaxV()); tessellator.addVertexWithUV(x+1, y+1, z , (double)up.getMaxU(), (double)up.getMinV()); tessellator.addVertexWithUV(x , y+1, z , (double)up.getMinU(), (double)up.getMinV()); tessellator.addVertexWithUV(x , y+1, z+1, (double)up.getMinU(), (double)up.getMaxV()); //North 2 tessellator.addVertexWithUV(x , y , z , (double)north.getMaxU(), (double)north.getMaxV()); tessellator.addVertexWithUV(x , y+1, z , (double)north.getMaxU(), (double)north.getMinV()); tessellator.addVertexWithUV(x+1, y+1, z , (double)north.getMinU(), (double)north.getMinV()); tessellator.addVertexWithUV(x+1, y , z , (double)north.getMinU(), (double)north.getMaxV()); //South 3 tessellator.addVertexWithUV(x+1, y , z+1, (double)south.getMaxU(), (double)south.getMaxV()); tessellator.addVertexWithUV(x+1, y+1, z+1, (double)south.getMaxU(), (double)south.getMinV()); tessellator.addVertexWithUV(x , y+1, z+1, (double)south.getMinU(), (double)south.getMinV()); tessellator.addVertexWithUV(x , y , z+1, (double)south.getMinU(), (double)south.getMaxV()); //West 4 tessellator.addVertexWithUV(x , y , z+1, (double)west.getMaxU(), (double)west.getMaxV()); tessellator.addVertexWithUV(x , y+1, z+1, (double)west.getMaxU(), (double)west.getMinV()); tessellator.addVertexWithUV(x , y+1, z , (double)west.getMinU(), (double)west.getMinV()); tessellator.addVertexWithUV(x , y , z , (double)west.getMinU(), (double)west.getMaxV()); //East 5 tessellator.addVertexWithUV(x+1, y , z , (double)east.getMaxU(), (double)east.getMaxV()); tessellator.addVertexWithUV(x+1, y+1, z , (double)east.getMaxU(), (double)east.getMinV()); tessellator.addVertexWithUV(x+1, y+1, z+1, (double)east.getMinU(), (double)east.getMinV()); tessellator.addVertexWithUV(x+1, y , z+1, (double)east.getMinU(), (double)east.getMaxV()); return true; } It does not rotate the textures at this point. But it seems to work so far, but with one problem. Depending on different angles when moving around the block, the textures seem to flicker some times between just a black pane and the expected texture... does anyone know why? Next question would be, where in this method do I have to do the rotation with the renderer.uvRotate* thingy? Edit: the "flickering" does occur on all placed blocks at the same time when looking at them from some angles
June 15, 201411 yr Hi The black is probably because you haven't set up the lighting and brightness, so it is using the settings from the last thing it rendered. This is typically done using something like tessellator.setBrightness(par1Block.getMixedBrightnessForBlock(this.blockAccess, wx, wy, wz); // wx,wy,wz = world coordinates tessellator.setColorOpaque_F(red, green, blue); // from 0.0 - 1.0 If you want to rotate the faces using uvRotate, you need to call RenderBlocks.renderStandardBlock or RenderBlocks.render after setting the flags. See vanilla RenderBlocks.renderBlockLog for a good example. The rotation is a bit strange, sometimes it flips the faces. But if that doesn't bother you then you don't need the Tessellator at all. -TGG
June 16, 201411 yr Author Ok finally had the time to give it a try and it works like a charm if I just don't use the tessellator and therefore use the RenderBlocks object. Rotation is easily done and for the lighting is no additional setup neccessary. I will post the code here if anyone else needs a reference Thanks again! @Override public boolean renderWorldBlock(IBlockAccess world, int x, int y, int z, Block block, int modelId, RenderBlocks renderer) { IIcon up = block.getIcon(world, x, y, z, 1); IIcon down = block.getIcon(world, x, y, z, 0); IIcon north = block.getIcon(world, x, y, z, 2); IIcon south = block.getIcon(world, x, y, z, 3); IIcon west = block.getIcon(world, x, y, z, 4); IIcon east = block.getIcon(world, x, y, z, 5); renderer.renderFaceXNeg(block, x, y, z, west); renderer.renderFaceXPos(block, x, y, z, east); renderer.renderFaceYNeg(block, x, y, z, down); renderer.renderFaceYPos(block, x, y, z, up); renderer.renderFaceZNeg(block, x, y, z, north); renderer.renderFaceZPos(block, x, y, z, south); TileEntity tile = world.getTileEntity(x, y, z); if(tile instanceof TileEntityMyTile){ //wonky rendering incoming switch(((TileEntityMyTile)tile).orientation.ordinal()){ case 0: //Bottom renderer.uvRotateNorth=2; //west renderer.uvRotateSouth=1; //east renderer.uvRotateWest=2; //south renderer.uvRotateEast=1; //north break; case 1: //Top renderer.uvRotateNorth=1; renderer.uvRotateSouth=2; renderer.uvRotateWest=1; renderer.uvRotateEast=2; break; case 2: //North renderer.uvRotateTop = 1; renderer.uvRotateBottom = 2; break; case 3: //South renderer.uvRotateTop=2; renderer.uvRotateBottom=1; renderer.uvRotateNorth=3; renderer.flipTexture=true; //east break; case 4: //West renderer.uvRotateTop=4; renderer.uvRotateBottom=4; break; case 5: //East renderer.uvRotateTop=3; renderer.uvRotateBottom=3; renderer.flipTexture=true; break; } } boolean flag = renderer.renderStandardBlock(block, x, y, z); //important reset afterwards! renderer.flipTexture=false; renderer.uvRotateNorth=0; //west renderer.uvRotateSouth=0; //east renderer.uvRotateWest=0; //south renderer.uvRotateEast=0; //north renderer.uvRotateTop=0; renderer.uvRotateBottom=0; return flag; }
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.