- Home /
change color of the selected triangles inside human chest
hi,
How to change the color of triangles inside the human mesh.I have applied the following code to change the color of the chest inside the human mesh.
void Update () {
MeshFilter mf = GetComponent<MeshFilter>();
if (mf == null) return;
Mesh mesh = mf.mesh;
int[] triangles = mesh.triangles;
Vector3[] vertices = mesh.vertices;
int[] trianglesNew = new int[triangles.Length];
Vector3[] verticesNew = new Vector3[triangles.Length];
for (int i = 0; i < trianglesNew.Length; i++)
{
Vector3 v3Pos = vertices[triangles[i]];
trianglesNew[i] = i;
verticesNew[i] = v3Pos;
}
Color colorT = Color.red;
Color[] colors = new Color[trianglesNew.Length];
for (int i = 0; i < colors.Length; i++)
{
colorT = new Color(Random.Range(0.0f, 1.0f), Random.Range(0.0f, 1.0f), Random.Range(0.0f, 1.0f), 1.0f);
colors[i] = colorT;
}
mesh.vertices = verticesNew;
mesh.triangles = trianglesNew;
mesh.colors = colors;
mesh.RecalculateBounds();
mesh.RecalculateNormals();
}
and i dont want to change the color of the whole material by specifying like this renderer.material.color = color.green;
For eg:- i like to take the spine and shoulder left,shoulder right joints and there from i want to took some chest points and change the color of the chest triangles to colors like green or red.
and my doubt is whether mesh.colors= colors has any effect on the object that we are trying to change.
Please clarify my doubt...
Thanks
Answer by robertbu · Sep 08, 2014 at 08:58 PM
First, making chnagres to the colors array is the way to change the color of individual triangles, BUT it only works is the shader used in the material for your mesh supports vertex colors. Only a few of the shaders that ship with Unity support vertex colors. So if you are not seeing color changes, then you probably are not using a shader that supports vertex colors.
But in looking at your code, I'm confused about a few other things. In changing colors, there is no reason to mess with the vertices of the mesh. For just changing the color of some triangles, you can cut your code down to:
void Update() {
MeshFilter mf = GetComponent<MeshFilter>();
if (mf == null) return;
Mesh mesh = mf.mesh;
Color[] colors = mesh.colors;
for (int i = 0; i < colors.Length; i++)
{
colors[i] = new Color(Random.Range(0.0f, 1.0f), Random.Range(0.0f, 1.0f), Random.Range(0.0f, 1.0f), 1.0f);
}
mesh.colors = colors;
}
Note that in general, the number of vertices in a mesh does not match the number of triangles in the triangle array. And that the colors array is the size of the vertices in the mesh, not the size of the triangles array. I know this is just a test, but if this was your real code, you would want to avoid the GetComponent() call every frame. You could get it once in Awake() or Start(). Also note that using the 'new' operator to construct a new colors array is fine in general, but since your goal here is to only color specific triangles, then your code will want a copy of the original colors as I've done here. In fact, you could get the colors array once in start and cache it, and then make changes and reassign as necessary.
Thanks for your reply.
I am using unity version 4.5 and as per your thought i applied simple shader program and tried to check for compatibility and the color of the human model material changed as per the shader program.
Shader "Custom/VertexInputSimple" {
SubShader {
Pass {
CGPROGRA$$anonymous$$
#pragma vertex vert
#pragma fragment frag
#include "UnityCG.cginc"
struct v2f {
float4 pos : SV_POSITION;
fixed4 color : COLOR;
};
v2f vert (appdata_base v)
{
v2f o;
o.pos = mul (UNITY_$$anonymous$$ATRIX_$$anonymous$$VP, v.vertex);
o.color.xyz = v.normal * 0.5 + 0.5;
o.color.w = 1.0;
return o;
}
fixed4 frag (v2f i) : COLOR0 { return i.color; }
ENDCG
}
}
}
output:
After that i applied your code in Update() in meshchange.cs.But it seems that the code has not done anything upon changing the color of the triangles.
Still i am confused about the mesh.colors = colors. for what reason it is used...
and my another question is how to apply color change for some part of chest in the above shader program.
I don't know why your triangles are not changing color. The above looks like a wireframe, and I'm no shader expert to know if this shader has issues with vertex colors. Back off and get vertex colors working with something simple like a cube. There are a number of shaders in the Unity Wiki that are vertex shaders. Your code above should work fine, though I'm not sure what you will see if you change your colors every frame (I'm away from my desktop and cannot test it).
Still i am confused about the mesh.colors = colors. for what reason it is used...
When you do:
Color[] colors = mesh.colors;
The array returned is a copy of the one internal to the mesh, not a reference to the original. So when you do:
mesh.colors = colors;
...under the hood, the colors in your array are being copied back into an internal data structure of the mesh.
As for wanting to change the color of the chest area, you are going to have to figure out some mechanism to identify the triangles to color. I could be based on distance...identify all triangles that have one (or all) vertices within a particular distance. I may be (or additionally) based on the normal. All the triangles that are facing a particular direction. Or you may identify submeshes in your model authoring program, and a hit anywhere in a submesh makes everything in that submesh change color. And I'm sure there are other solutions.