Jump to content

[1.8] [SOLVED] Manipulating model in ISmartBlockModel.handleBlockState()


SnowyEgret

Recommended Posts

Hi,

 

I have implemented ISmartModel as instructed in TheGreyGhost's MBE04 tutorial. Things are working fine. In handleBlockState() I am looking up a model from an IBlockState I get from an unlisted property of the incoming IExtendedBlockState.

 

Before returning the model, can I manipulate it? I am attempting to find a way to modify the color of it's texture (I posted a couple of days ago on this).  There is a method returning the model's texture (of class TextureAtlasSprite), and a method to get the texture's texture data which is also setable. My printlns seem to indicate the texture data is changed, but I am not seeing any difference to the texture in game.

 

Here is my implentation of ISmartModel:

 

package ds.plato.block;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import net.minecraft.block.state.IBlockState;
import net.minecraft.client.Minecraft;
import net.minecraft.client.renderer.block.model.BakedQuad;
import net.minecraft.client.renderer.block.model.ItemCameraTransforms;
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
import net.minecraft.client.resources.model.IBakedModel;
import net.minecraft.client.resources.model.ModelResourceLocation;
import net.minecraft.util.EnumFacing;
import net.minecraftforge.client.model.IFlexibleBakedModel;
import net.minecraftforge.client.model.ISmartBlockModel;
import net.minecraftforge.common.property.IExtendedBlockState;
import net.minecraftforge.common.property.IUnlistedProperty;

public class BlockSelectedModel implements ISmartBlockModel {

public static ModelResourceLocation modelResourceLocation = new ModelResourceLocation("plato:blockSelected");
private IBakedModel defaultModel;
private IUnlistedProperty prevBlockProperty;

public BlockSelectedModel(IBakedModel defaultModel, PropertyPreviousBlock prevBlockProperty) {
	super();
	this.defaultModel = defaultModel;
	this.prevBlockProperty = prevBlockProperty;
}

@Override
public IBakedModel handleBlockState(IBlockState state) {
	assert IExtendedBlockState.class.isAssignableFrom(state.getClass());
	IBlockState s = ((IExtendedBlockState) state).getValue(prevBlockProperty);
	IBakedModel model = Minecraft.getMinecraft().getBlockRendererDispatcher().getBlockModelShapes()
			.getModelForState(s);

	IFlexibleBakedModel m = (IFlexibleBakedModel)model;

	TextureAtlasSprite t = m.getTexture();
	int[][] td = t.getFrameTextureData(0);
	System.out.println(Arrays.deepToString(td));

	td = modifyTextureData(td);
	List l = new ArrayList();
	l.add(td);
	t.setFramesTextureData(l);

	t = m.getTexture();
	td = t.getFrameTextureData(0);
	System.out.println(Arrays.deepToString(td));

	return m;
}

@Override
public List getFaceQuads(EnumFacing p_177551_1_) {
	// TODO Auto-generated method stub
	return null;
}

@Override
public List getGeneralQuads() {
	// TODO Auto-generated method stub
	return null;
}

@Override
public boolean isAmbientOcclusion() {
	// TODO Auto-generated method stub
	return false;
}

@Override
public boolean isGui3d() {
	// TODO Auto-generated method stub
	return false;
}

@Override
public boolean isBuiltInRenderer() {
	// TODO Auto-generated method stub
	return false;
}

@Override
public TextureAtlasSprite getTexture() {
	return defaultModel.getTexture();
}

@Override
public ItemCameraTransforms getItemCameraTransforms() {
	// TODO Auto-generated method stub
	return null;
}

// Private-------------------------------------------------------------

private int[][] modifyTextureData(int[][] data) {
	for (int i = 0; i < data.length; i++) {
		for (int j = 0; j < data[i].length; j++) {
			data[i][j] = 0;
		}
	}
	return data;
}

}

 

For testing purposes I am just setting the texture data to 0. Seems I can cast the IBakedModel to an IFlexibleBakedModel, for whatever that's worth.

Link to comment
Share on other sites

Hi

 

the getTexture method is not generally used for rendering the block  - it is used (for example) for the 'exploding shards' that you get when you destroy a block by digging it.

 

In order to change the texture, you will need to change the BakedQuad data (each BakedQuad in your BlockModel is made up of four corners (vertices) - and at each vertex, it records the [x,y,z] position as well as a texture coordinate [u,v]. 

 

All of the textures for blocks and item models are "stitched together" into a large texture sheet, see the "Texture Coordinates" diagram on this page halfway down

http://greyminecraftcoder.blogspot.co.at/2014/12/the-tessellator-and-worldrenderer-18.html

 

You will need to create your BakedQuads with the correct texture coordinates of the new texture

An example of how you can do this is in MBE15, this class works for the faces of the cube

https://github.com/TheGreyGhost/MinecraftByExample/blob/master/src/main/java/minecraftbyexample/mbe15_item_smartitemmodel/ChessboardSmartItemModel.java

see createBakedQuadForFace().

FaceBakery.makeBakedQuad() can be useful for generating quads

 

If you want to change a model with arbitrary quads (not just the NEWSUD faces of the cube) then you can probably read the quads from the base model one by one, convert the int arrays to vertex data, replace the [u,v] with the new [u,v], and create a new list of BakedQuads from it.  Haven't tried it, but it should work.

 

-TGG

Link to comment
Share on other sites

Thanks TGG for the response.

 

I think the last, more generic, method you proposed is the way I need to go. Just a few questions to begin. Here is a start for new handleBlockState():

 

	@Override
public IBakedModel handleBlockState(IBlockState state) {
	assert IExtendedBlockState.class.isAssignableFrom(state.getClass());
	IBlockState s = ((IExtendedBlockState) state).getValue(prevBlockProperty);
	IBakedModel model = Minecraft.getMinecraft().getBlockRendererDispatcher().getBlockModelShapes()
			.getModelForState(s);

	IFlexibleBakedModel m = (IFlexibleBakedModel) model;

	VertexFormat format = m.getFormat();
	System.out.println("format=" + format);

	List<BakedQuad> generalQuads = m.getGeneralQuads();
	System.out.println(Arrays.toString(generalQuads.toArray()));
	for (BakedQuad q : generalQuads) {
		int[] vd = q.getVertexData();
		System.out.println(Arrays.toString(vd));
	}

	for (EnumFacing face : EnumFacing.values()) {
		List<BakedQuad> faceQuads = m.getFaceQuads(face);
		for (BakedQuad q : faceQuads) {
			int[] vd = q.getVertexData();
			System.out.println(Arrays.toString(vd));
		}
	}

	return m;
}

 

When I run and select a vanila block sand, it appears to have no generalQuad data(the list of BakedQuads is empty), only faceQuad data. Can I assume that any model which has more than 6 standard sides will implement getGeneralQuads()?

 

Here is the output of vertex data from the faceQuads:

 

[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 0, 1065353216, -8421505, 1058537800, 1046480159, 0, 0, 0, 0, -8421505, 1058537800, 1048574689, 0, 1065353216, 0, 0, -8421505, 1059061432, 1048574689, 0, 1065353216, 0, 1065353216, -8421505, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 1065353216, 0, -1, 1058537800, 1046480159, 0, 0, 1065353216, 1065353216, -1, 1058537800, 1048574689, 0, 1065353216, 1065353216, 1065353216, -1, 1059061432, 1048574689, 0, 1065353216, 1065353216, 0, -1, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [1065353216, 1065353216, 0, -3355444, 1058537800, 1046480159, 0, 1065353216, 0, 0, -3355444, 1058537800, 1048574689, 0, 0, 0, 0, -3355444, 1059061432, 1048574689, 0, 0, 1065353216, 0, -3355444, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 1065353216, 1065353216, -3355444, 1058537800, 1046480159, 0, 0, 0, 1065353216, -3355444, 1058537800, 1048574689, 0, 1065353216, 0, 1065353216, -3355444, 1059061432, 1048574689, 0, 1065353216, 1065353216, 1065353216, -3355444, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 1065353216, 0, -6710887, 1058537800, 1046480159, 0, 0, 0, 0, -6710887, 1058537800, 1048574689, 0, 0, 0, 1065353216, -6710887, 1059061432, 1048574689, 0, 0, 1065353216, 1065353216, -6710887, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [1065353216, 1065353216, 1065353216, -6710887, 1058537800, 1046480159, 0, 1065353216, 0, 1065353216, -6710887, 1058537800, 1048574689, 0, 1065353216, 0, 0, -6710887, 1059061432, 1048574689, 0, 1065353216, 1065353216, 0, -6710887, 1059061432, 1046480159, 0]

 

Do I use the format from VertexFormat format = m.getFormat() to interpret these arrays of ints?

 

Also, there is no setQuads() method on IFlexibleBakedModel. Is this going to be a problem?

Link to comment
Share on other sites

Thanks TGG for the response.

You're welcome :)

 

When I run and select a vanila block sand, it appears to have no generalQuad data(the list of BakedQuads is empty), only faceQuad data. Can I assume that any model which has more than 6 standard sides will implement getGeneralQuads()?

Yes.  But in general a model may have any mixture of faceQuads and GeneralQuads - it may have all faceQuads, all generalQuads, or a mixture of both.  faceQuads is mostly useful for blocks which don't draw some of their faces when they are next to each other.  For example stone.  Two stone blocks next to each other don't need to draw the two faces where they are touching.

 

General quads are usually for odd-shaped faces such as the torch, or the ladder.

 

Here is the output of vertex data from the faceQuads:

 

[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 0, 1065353216, -8421505, 1058537800, 1046480159, 0, 0, 0, 0, -8421505, 1058537800, 1048574689, 0, 1065353216, 0, 0, -8421505, 1059061432, 1048574689, 0, 1065353216, 0, 1065353216, -8421505, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 1065353216, 0, -1, 1058537800, 1046480159, 0, 0, 1065353216, 1065353216, -1, 1058537800, 1048574689, 0, 1065353216, 1065353216, 1065353216, -1, 1059061432, 1048574689, 0, 1065353216, 1065353216, 0, -1, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [1065353216, 1065353216, 0, -3355444, 1058537800, 1046480159, 0, 1065353216, 0, 0, -3355444, 1058537800, 1048574689, 0, 0, 0, 0, -3355444, 1059061432, 1048574689, 0, 0, 1065353216, 0, -3355444, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 1065353216, 1065353216, -3355444, 1058537800, 1046480159, 0, 0, 0, 1065353216, -3355444, 1058537800, 1048574689, 0, 1065353216, 0, 1065353216, -3355444, 1059061432, 1048574689, 0, 1065353216, 1065353216, 1065353216, -3355444, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [0, 1065353216, 0, -6710887, 1058537800, 1046480159, 0, 0, 0, 0, -6710887, 1058537800, 1048574689, 0, 0, 0, 1065353216, -6710887, 1059061432, 1048574689, 0, 0, 1065353216, 1065353216, -6710887, 1059061432, 1046480159, 0]
[19:27:02] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:55]: [1065353216, 1065353216, 1065353216, -6710887, 1058537800, 1046480159, 0, 1065353216, 0, 1065353216, -6710887, 1058537800, 1048574689, 0, 1065353216, 0, 0, -6710887, 1059061432, 1048574689, 0, 1065353216, 1065353216, 0, -6710887, 1059061432, 1046480159, 0]

 

Do I use the format from VertexFormat format = m.getFormat() to interpret these arrays of ints?

Yes - you need to find the offset corresponding to VertexFormatElement.EnumUsage UV.

If it's the standard format, vertexToInts() in this class

https://github.com/TheGreyGhost/MinecraftByExample/blob/master/src/main/java/minecraftbyexample/mbe15_item_smartitemmodel/ChessboardSmartItemModel.java

gives you the info you need - also shows you how to go from float to int, you just need to find the function to go back the other way from rawInts to float

If you want to code for any generic VertextFormat, I think you should be able to iterate through its elements, find the one for UV, and get its offset.

 

Also, there is no setQuads() method on IFlexibleBakedModel. Is this going to be a problem?

No problem.  Just create your own class extending IFlexibleBakedmodel and store your modified BakedQuads in it, then return it from handleBlockState.  When your IFlexibleBakedModel instance is called i.e.getGeneralQuads or getFaceQuads, return your modified BakedQuads.

 

-TGG

 

 

 

 

Link to comment
Share on other sites

I have answered the last part of my question. Instead of returning the model looked up in handleBlockState() I return this (which is an IBakedModel). This gives me the oportunity to modify or rebuild the BakedQuads list returned from getFaceQuads() and getGeneralQuads():

 

package ds.plato.block;

import java.util.Arrays;
import java.util.List;
import net.minecraft.block.state.IBlockState;
import net.minecraft.client.Minecraft;
import net.minecraft.client.renderer.block.model.BakedQuad;
import net.minecraft.client.renderer.block.model.ItemCameraTransforms;
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
import net.minecraft.client.renderer.vertex.VertexFormat;
import net.minecraft.client.resources.model.IBakedModel;
import net.minecraft.client.resources.model.ModelResourceLocation;
import net.minecraft.util.EnumFacing;
import net.minecraftforge.client.model.IFlexibleBakedModel;
import net.minecraftforge.client.model.ISmartBlockModel;
import net.minecraftforge.common.property.IExtendedBlockState;
import net.minecraftforge.common.property.IUnlistedProperty;

public class BlockSelectedModel implements ISmartBlockModel {

public static ModelResourceLocation modelResourceLocation = new ModelResourceLocation("plato:blockSelected");
private IBakedModel defaultModel;
private IFlexibleBakedModel model;
private IUnlistedProperty selectedBlockProperty;

public BlockSelectedModel(IBakedModel defaultModel, PropertySelectedBlock selectedBlockProperty) {
	this.defaultModel = defaultModel;
	this.selectedBlockProperty = selectedBlockProperty;
}

@Override
public IBakedModel handleBlockState(IBlockState state) {
	assert IExtendedBlockState.class.isAssignableFrom(state.getClass());
	IBlockState s = ((IExtendedBlockState) state).getValue(selectedBlockProperty);
	System.out.println("Selected block="+s);
	IBakedModel m = Minecraft.getMinecraft().getBlockRendererDispatcher().getBlockModelShapes().getModelForState(s);
	model = (IFlexibleBakedModel) m;
	return this;
}

@Override
public List getFaceQuads(EnumFacing face) {
	List<BakedQuad> faceQuads = model.getFaceQuads(face);
	for (BakedQuad q : faceQuads) {
		int[] vd = q.getVertexData();
		System.out.println(Arrays.toString(vd));
	}
	//Modify list here
	return faceQuads;
}

@Override
public List getGeneralQuads() {
	List<BakedQuad> generalQuads = model.getGeneralQuads();
	System.out.println(Arrays.toString(generalQuads.toArray()));
	for (BakedQuad q : generalQuads) {
		int[] vd = q.getVertexData();
		System.out.println(Arrays.toString(vd));
	}
	//Modify list here
	return generalQuads;
}

@Override
public boolean isAmbientOcclusion() {
	return model.isAmbientOcclusion();
}

@Override
public boolean isGui3d() {
	return model.isGui3d();
}

@Override
public boolean isBuiltInRenderer() {
	return model.isBuiltInRenderer();
}

@Override
public TextureAtlasSprite getTexture() {
	// return defaultModel.getTexture();
	return model.getTexture();
}

@Override
public ItemCameraTransforms getItemCameraTransforms() {
	return model.getItemCameraTransforms();
}
}

 

This runs fine. My questions are:

 

Why does BakedQuad.getVertexData() return ints, and what do they mean?

The vertex data seems to be the same for every model looked up in handleBlockState():

 

[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:35]: Selected block=minecraft:sand[variant=sand]
[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 0, 1065353216, -8421505, 1058537800, 1046480159, 0, 0, 0, 0, -8421505, 1058537800, 1048574689, 0, 1065353216, 0, 0, -8421505, 1059061432, 1048574689, 0, 1065353216, 0, 1065353216, -8421505, 1059061432, 1046480159, 0]
[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 1065353216, 0, -1, 1058537800, 1046480159, 0, 0, 1065353216, 1065353216, -1, 1058537800, 1048574689, 0, 1065353216, 1065353216, 1065353216, -1, 1059061432, 1048574689, 0, 1065353216, 1065353216, 0, -1, 1059061432, 1046480159, 0]
[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [1065353216, 1065353216, 0, -3355444, 1058537800, 1046480159, 0, 1065353216, 0, 0, -3355444, 1058537800, 1048574689, 0, 0, 0, 0, -3355444, 1059061432, 1048574689, 0, 0, 1065353216, 0, -3355444, 1059061432, 1046480159, 0]
[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 1065353216, 1065353216, -3355444, 1058537800, 1046480159, 0, 0, 0, 1065353216, -3355444, 1058537800, 1048574689, 0, 1065353216, 0, 1065353216, -3355444, 1059061432, 1048574689, 0, 1065353216, 1065353216, 1065353216, -3355444, 1059061432, 1046480159, 0]
[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 1065353216, 0, -6710887, 1058537800, 1046480159, 0, 0, 0, 0, -6710887, 1058537800, 1048574689, 0, 0, 0, 1065353216, -6710887, 1059061432, 1048574689, 0, 0, 1065353216, 1065353216, -6710887, 1059061432, 1046480159, 0]
[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [1065353216, 1065353216, 1065353216, -6710887, 1058537800, 1046480159, 0, 1065353216, 0, 1065353216, -6710887, 1058537800, 1048574689, 0, 1065353216, 0, 0, -6710887, 1059061432, 1048574689, 0, 1065353216, 1065353216, 0, -6710887, 1059061432, 1046480159, 0]
[10:21:59] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getGeneralQuads:55]: []

{ds.plato.block.PropertySelectedBlock@15af3a9b=Optional.of(minecraft:dirt[snowy=false,variant=dirt])}
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:handleBlockState:35]: Selected block=minecraft:dirt[snowy=false,variant=dirt]
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 0, 1065353216, -8421505, 1048576655, 1044383007, 0, 0, 0, 0, -8421505, 1048576655, 1046477537, 0, 1065353216, 0, 0, -8421505, 1049623921, 1046477537, 0, 1065353216, 0, 1065353216, -8421505, 1049623921, 1044383007, 0]
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 1065353216, 0, -1, 1048576655, 1044383007, 0, 0, 1065353216, 1065353216, -1, 1048576655, 1046477537, 0, 1065353216, 1065353216, 1065353216, -1, 1049623921, 1046477537, 0, 1065353216, 1065353216, 0, -1, 1049623921, 1044383007, 0]
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [1065353216, 1065353216, 0, -3355444, 1048576655, 1044383007, 0, 1065353216, 0, 0, -3355444, 1048576655, 1046477537, 0, 0, 0, 0, -3355444, 1049623921, 1046477537, 0, 0, 1065353216, 0, -3355444, 1049623921, 1044383007, 0]
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 1065353216, 1065353216, -3355444, 1048576655, 1044383007, 0, 0, 0, 1065353216, -3355444, 1048576655, 1046477537, 0, 1065353216, 0, 1065353216, -3355444, 1049623921, 1046477537, 0, 1065353216, 1065353216, 1065353216, -3355444, 1049623921, 1044383007, 0]
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [0, 1065353216, 0, -6710887, 1048576655, 1044383007, 0, 0, 0, 0, -6710887, 1048576655, 1046477537, 0, 0, 0, 1065353216, -6710887, 1049623921, 1046477537, 0, 0, 1065353216, 1065353216, -6710887, 1049623921, 1044383007, 0]
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getFaceQuads:46]: [1065353216, 1065353216, 1065353216, -6710887, 1048576655, 1044383007, 0, 1065353216, 0, 1065353216, -6710887, 1048576655, 1046477537, 0, 1065353216, 0, 0, -6710887, 1049623921, 1046477537, 0, 1065353216, 1065353216, 0, -6710887, 1049623921, 1044383007, 0]
[10:22:06] [Client thread/INFO] [sTDOUT]: [ds.plato.block.BlockSelectedModel:getGeneralQuads:55]: []

 

 

Link to comment
Share on other sites

Ok, after looking closely at your excelent example, I've come up with this really simple solution which works ...almost.

 

package ds.plato.block;

import java.awt.Color;
import java.util.List;

import net.minecraft.block.state.IBlockState;
import net.minecraft.client.Minecraft;
import net.minecraft.client.renderer.block.model.BakedQuad;
import net.minecraft.client.renderer.block.model.ItemCameraTransforms;
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
import net.minecraft.client.resources.model.IBakedModel;
import net.minecraft.client.resources.model.ModelResourceLocation;
import net.minecraft.util.EnumFacing;
import net.minecraftforge.client.model.ISmartBlockModel;
import net.minecraftforge.common.property.IExtendedBlockState;
import net.minecraftforge.common.property.IUnlistedProperty;

public class BlockSelectedModel implements ISmartBlockModel {

public static ModelResourceLocation modelResourceLocation = new ModelResourceLocation("plato:blockSelected");
private IBakedModel defaultModel, model;
private IUnlistedProperty selectedBlockProperty;
private final int tint = Color.RED.getRed();

public BlockSelectedModel(IBakedModel defaultModel, PropertySelectedBlock selectedBlockProperty) {
	this.defaultModel = defaultModel;
	this.selectedBlockProperty = selectedBlockProperty;
}

@Override
public IBakedModel handleBlockState(IBlockState state) {
	assert IExtendedBlockState.class.isAssignableFrom(state.getClass());
	IBlockState s = ((IExtendedBlockState) state).getValue(selectedBlockProperty);
	model = Minecraft.getMinecraft().getBlockRendererDispatcher().getBlockModelShapes().getModelForState(s);
	return this;
}

@Override
public List getFaceQuads(EnumFacing face) {
	List<BakedQuad> faceQuads = model.getFaceQuads(face);
	for (BakedQuad q : faceQuads) {
		q = new BakedQuad(tint(q.getVertexData()), 0, face);
	}
	return faceQuads;
}

@Override
public List getGeneralQuads() {
	List<BakedQuad> generalQuads = model.getGeneralQuads();
	for (BakedQuad q : generalQuads) {
		q = new BakedQuad(tint(q.getVertexData()), 0, q.getFace());
	}
	return generalQuads;
}

@Override
public boolean isAmbientOcclusion() {
	return model.isAmbientOcclusion();
}

@Override
public boolean isGui3d() {
	return model.isGui3d();
}

@Override
public boolean isBuiltInRenderer() {
	return model.isBuiltInRenderer();
}

@Override
public TextureAtlasSprite getTexture() {
	return model.getTexture();
}

@Override
public ItemCameraTransforms getItemCameraTransforms() {
	return model.getItemCameraTransforms();
}

// Private-----------------------------------------------------

private int[] tint(int[] vertexData) {
	//int[] vd = new int[vertexData.length];
	//System.arraycopy(vertexData, 0, vd, 0, vertexData.length);
	int[] vd = vertexData;
	vd[3] = tint;
	vd[10] = tint;
	vd[17] = tint;
	vd[24] = tint;
	return vd;
}

}

 

Just to recap, I am replacing the selected block with a new block that uses the model of the selected block. I modify to vertex data to tint the texture red. This works fine! :)

 

The only problem is that some, but not all, of the blocks of the same type as the selected block are also tinted red:

 

2015-05-12_17.04.26.png

 

(How do I insert an image? file://~/image.png?, i'm on ubuntu.)

 

If I return a copy of the new vertex data arrray as commented out in private method tint(), the problem goes away, but my block is not tinted.

 

Any help appreciated.

Link to comment
Share on other sites

Solved my problems. Works great.

 

package ds.plato.block;

import java.awt.Color;
import java.util.ArrayList;
import java.util.List;

import net.minecraft.block.state.IBlockState;
import net.minecraft.client.Minecraft;
import net.minecraft.client.renderer.block.model.BakedQuad;
import net.minecraft.client.renderer.block.model.ItemCameraTransforms;
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
import net.minecraft.client.resources.model.IBakedModel;
import net.minecraft.client.resources.model.ModelResourceLocation;
import net.minecraft.util.EnumFacing;
import net.minecraftforge.client.model.ISmartBlockModel;
import net.minecraftforge.common.property.IExtendedBlockState;
import net.minecraftforge.common.property.IUnlistedProperty;

public class BlockSelectedModel implements ISmartBlockModel {

public static ModelResourceLocation modelResourceLocation = new ModelResourceLocation("plato:blockSelected");
private IBakedModel defaultModel, model;
private IUnlistedProperty selectedBlockProperty;
private final int tint = Color.RED.getRed();

public BlockSelectedModel(IBakedModel defaultModel, PropertySelectedBlock selectedBlockProperty) {
	this.defaultModel = defaultModel;
	this.selectedBlockProperty = selectedBlockProperty;
}

@Override
public IBakedModel handleBlockState(IBlockState state) {
	assert IExtendedBlockState.class.isAssignableFrom(state.getClass());
	IBlockState s = ((IExtendedBlockState) state).getValue(selectedBlockProperty);
	model = Minecraft.getMinecraft().getBlockRendererDispatcher().getBlockModelShapes().getModelForState(s);
	return this;
}

@Override
public List getFaceQuads(EnumFacing face) {
	List<BakedQuad> quads = new ArrayList<>();
	List<BakedQuad> faceQuads = model.getFaceQuads(face);
	for (BakedQuad q : faceQuads) {
		quads.add(new BakedQuad(tint(q.getVertexData()), 0, face));
	}
	return quads;
}

@Override
public List getGeneralQuads() {
	List<BakedQuad> quads = new ArrayList<>();
	List<BakedQuad> generalQuads = model.getGeneralQuads();
	for (BakedQuad q : generalQuads) {
		quads.add( new BakedQuad(tint(q.getVertexData()), 0, q.getFace()));
	}
	return quads;
}

@Override
public boolean isAmbientOcclusion() {
	return model.isAmbientOcclusion();
}

@Override
public boolean isGui3d() {
	return model.isGui3d();
}

@Override
public boolean isBuiltInRenderer() {
	return model.isBuiltInRenderer();
}

@Override
public TextureAtlasSprite getTexture() {
	return model.getTexture();
}

@Override
public ItemCameraTransforms getItemCameraTransforms() {
	return model.getItemCameraTransforms();
}

// Private-----------------------------------------------------

private int[] tint(int[] vertexData) {
	int[] vd = new int[vertexData.length];
	System.arraycopy(vertexData, 0, vd, 0, vertexData.length);
	vd[3] = tint;
	vd[10] = tint;
	vd[17] = tint;
	vd[24] = tint;
	return vd;
}

}

 

Thanks TGG!

Link to comment
Share on other sites

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.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Announcements



  • Recently Browsing

    • No registered users viewing this page.
  • Posts

    • W杯バカラおすすめ↙BCGAME33·COM■北マケドニアバカラホールダンバW杯グランドレスカジノバカラコミュニティ[本社お問い合わせテレJBOX7]W杯バカラ◎=京畿フォックスウッドカジノバカラゲームW杯トンガW杯バカラ中継[総販お問い合わせカカオトークJBOX7]W杯バカラ◀♣クプンマリバーカラゲームW杯コートジボワールW杯バッカラ中継[各種オフィコミュニティ制作]ワールドカップバッカラ◀  경기京畿ベリーズバーカラホールダンバーカラコミュニティ[マーケティングお問い合わせ]ワールドカップバッカラ=▼戦略ネビスボンバーカラ제도戦略ネビスボンバーカラ W杯バカラリーグ[スポーツ本社]W杯バカラ←&ゲームウィンカジノバカラ賭博場W杯コロンビアW杯バカラ検証[ト本社お問い合わせ]W杯バカラ↗○グループトークハンガリーバカラ動画W杯ガーナW杯バカラ旅行[トト総販購入]W杯バカラ☞ 검증検証スウェーデンバーカラ住所ワールドカップパナマワールドカップパカラおすすめ[カジノ総販]ワールドカップバーカラ↔ª クープーン北アフリカバーカラサイトワールドカップフォールズビューカジノワールドカップバーカラリーグ[大和本社]ワールドカップバーカラ▩ 놀이터遊び場デンマークバーカラカジノパブワールドカップバーカラ カジノカップ バカラメーカー パラグアイ バカラトラベル [BCGAME BCゲーム総販に関するお問い合わせ] お知らせ設定 おすすめ購読いいですね
    • メジャーバットマンリーグ◎BCGAME33·COM■リヒテンシュタインバットマン放送メジャースーダンバットマン募集[本社お問い合わせテレJBOX7]メジャーバットマン♧*映像モナコバットマン放送メジャーアルバニアメジャーバットマン総販[総販お問い合わせカカオトークJBOX7]メジャーバットマン↗検証アンティークバットマンホールダンバー[各種オフィコミュニティ制作]メジャーベットメン♨♤戦略ナイジェリアベットメンバカラッパーリオールダムバクラージュ ナイジェリアメジャーバットマン賭博場[スポーツ本社]メジャーバットマン●↙検証モンテネグロバットマン競技メジャーガーナメジャーバットマン遊び場[トト本社お問い合わせ]メジャーバットマン▷◐中継モルドババットマン動画メジャーセーシェルメジャーバットマン競技[トト総販購入]メジャーバットマン♬♣業者モロッコベットメンホールダンパブメイザートリニダードメイザーベットメンリーグ[カジノ総販]メイザーベットメンº#ゲーム場パナマベットメン方法 メイザークラウンカジノボーン [競馬総販]ミャンマーベトナム旅行フォックスウッドカジノベトナムYouTube [BCGAMEBCゲーム総販お問い合わせ]お知らせ設定おすすめ購読いいですね
    • モバイルブラックジャック検証◐BCGAME33·COM▥アリアカジノブラックジャックホールダンバーモバイルボリビアブラックジャック動画[本社お問い合わせテレJBOX7]モバイルブラックジャック↓←動画パラオブラックジャックトーナメントモバイルラオスモバイルブラックジャックリーグ[総販お問い合わせカカオトークJBOX7]モバイルブラックジャック†▣ユーチューブセントビンセントブラックジャック放送モバイルオセアニアモバイルブラックザックアドレス[各種オフィコミュニティ制作]携帯 ブラックザック ♥リーグトルコ ブラックザック放送 モバイルエストニア モバイル ブラックザックホールダンバー [マーケティングお問い合わせ] モバイル ブラックザック⊙️ コミュニティ ロシア ブラックザック セントビル中継社 セント ブラックジャックトーナメント [スポーツ本社]モバイルブラックジャック↔º映像ソロモン諸島ブラックジャックサイトモバイルインドネシアモバイルブラックジャック遊び場[ト本社お問い合わせ]モバイルブラックジャック☜↔おすすめサハラブラックジャックコミュニティモバイルシザーズパレスカジノモバイルブラックジャック動画[トト総販購入]モバイルブラックジャック◁↑ツアーコンドミニアムサイト·トルクメニスタン· ブラックザックカジノパブ·モバイルベネズエラ·携帯電話 ブラックザック·コミュニティ[大和本社]携帯電話 ブラックザック▼ギャンブル場 コンゴ·ブラックザック·クラブ [スマト総販店]移動ブティヴティヴティヴティヴティヴティヴティヴティヴティーズ·携帯電話 BLACK JAPOON 本社 [競馬総販]ジブチ ブラックジャックおすすめ エクアドル ブラックジャック総販 [BCGAME BCゲーム総販お問い合わせ]お知らせ設定おすすめ購読いいですね
    • 射幸性食宝コミュニティ♤BCGAME33·COM▦ネビス食宝動画射幸性東アジア食宝検証[本社お問い合わせテレJBOX7]射幸性食宝♨↕コミュニティモルタ射幸性カメルーン射幸性食宝募集[総販お問い合わせカカオトークJBOX7]射幸性食宝▣▽遊び場シリア食宝戦略射幸性レソト射幸性食宝バカラパブ[各種オフィコミュニティ制作]賭博カザフスタン式報ポーカー大会賭博ゲーム賭博ゲームキャッシュラパブ[マーケティングお問い合わせ]賭博ゲーム賭博ゲーム ロシア食宝動画 射幸性ホンジュラス射幸性食宝遊び場 [ト本社お問い合わせ]射幸性食宝&ºキャッシュゲームフィジー食宝グループチャットルーム射幸性モナコ射幸性食宝トーナメント [トト総販購入]射幸性食宝♥↔ゲームドイツ食宝リーグ射幸性英国射幸性食宝ポーカー大会[カジノ総販]賭博師 ☏️ 業者アラブ式報検証賭博師小諸賭博場[ヤマト本社] 四行星式報 ※♠グループチャットルームベネズエラ式報遊び場四行星ドイツ四行成歩放送 [バカラ総販] スウェーデンサ行省式報放送
    • Tsuopy №BCGAME55·COM @ Opie总经销短道速滑Opie视频链接
  • Topics

×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.