-
|
|
Custom Effect not working properly with .x model
|
Quick note: I found it a bit frustrating when posting on this forum. forum admins, could you please make/request a simple Invision Power Board type forum system.
Ok now to the issue i'm having with effects and models. I was wondering if someone could explain to me why my model isn't being rendered properly. The colour is all wrong. Here are a couple of screenshots to help explain the situation:

(It's a bit dark, no idea why it came out like that in the DirectX viewer.) The body of the car is supposed to be green, with blue windows and black tires. But this is what it ends up like:

(ignore the red background) It's all yellow.
I've followed the code given in the tutorial about custom effects with models on MSDN. Here's the code:
| // Set the custom effect to the mesh parts |
| public void SetEffectFile(Model m, Effect EffectFile) |
| { |
| foreach (ModelMesh mesh in m.Meshes) |
| { |
| foreach (ModelMeshPart part in mesh.MeshParts) |
| { |
| part.Effect = EffectFile; |
| } |
| } |
| } |
| |
| // Renders the mesh using the custom effect |
| foreach (ModelMesh mesh in m.Meshes) |
| { |
| foreach (Effect effect in mesh.Effects) |
| { |
| effect.CurrentTechnique = EffectFile.Techniques["Simplest"]; |
| effect.Parameters["xViewProjection"].SetValue((transforms[mesh.ParentBone.Index] * final) * Camera.m_view * Camera.m_projection); |
| effect.Parameters["CameraPos"].SetValue(Camera.m_position); |
| effect.Parameters["WorldMat"].SetValue((transforms[mesh.ParentBone.Index] * final)); |
| } |
| mesh.Draw(); |
| } |
So is there something i'm missing? Is this actually supposed to work or are .x files the reason it isn't working?
Thanks!
Ankur
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
General Hank:Quick note: I found it a bit frustrating when posting on this forum. forum admins, could you please make/request a simple Invision Power Board type forum system.
You can make your own suggestions/bug reports by following the steps described here. The MS Connect site already contains some requests for an improved text box (the current one is hated by all), for which you can vote. But the forum structure is unlikely to change, because it was recently created in its current form.
General Hank:Ok now to the issue i'm having with effects and models
Inside you model/modelling package... how are the model's colors defined? are they defined through textures, or vertex colors, or material colors? Your shader will need to handle these cases.
Does the model draw well when you use BasicEffect? If so, here you can read about what the BasicEffect does in the background to handle many types of models and color data.
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
I had a feeling that it was something to do with that. When using basicEffect the model that is rendered is "coloured" correctly but with my custom effect it isn't. This is because the car i've modeled has different colored polygons (ie different materials) but on the same mesh. Here is a screenshot of the model in XSI. In the screenshot you can see that the car body is one mesh but has different materials for different parts of the mesh.

Ok, is there a way of extracting the material data for the different areas of the mesh and then sending them to the effect file?
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
I'd say that the best way to solve this would be to bake the colors into a texture, and use that to color your model. That way, you could even add numbers and other drawings on the car.
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
Can you show us the code for the shader you are using to draw this?
When a shader does not render the way you expect, the best way to debug this is using PIX for Windows: take a single frame capture of your game, then you can debug individual pixels and single-step through the shader code to see exactly what it is doing.
XNA Framework Developer -
blog - homepage
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
Hi,
Ok, here's my shader. I've copied the whole shader file here:
| float4x4 xViewProjection; |
| float4x4 WorldMat; |
| float3 CameraPos; |
| |
| struct VertexToPixel |
| { |
| float4 Position : POSITION; |
| float3 Normal : TEXCOORD0; |
| float3 WrldPos : TEXCOORD1; |
| float4 Color : COLOR0; |
| }; |
| |
| struct PixelToFrame |
| { |
| float4 Color : COLOR0; |
| }; |
| |
| VertexToPixel SimplestVertexShader( float3 inNorm : NORMAL, float4 inPos : POSITION, float4 inColor : COLOR0) |
| { |
| VertexToPixel Output = (VertexToPixel)0; |
| |
| Output.Position = mul(inPos, xViewProjection); |
| Output.WrldPos = mul(inPos, WorldMat); |
| Output.Normal = mul(inNorm, WorldMat); |
| |
| Output.Color = inColor; |
| |
| return Output; |
| } |
| |
| PixelToFrame OurFirstPixelShader(VertexToPixel Input) |
| { |
| PixelToFrame Output = (PixelToFrame)0; |
| |
| float3 unit_view_vec = normalize(CameraPos - Input.WrldPos); |
| |
| float3 LightPos = float3(0,50,0); |
| float4 LightCol = float4(1,1,1,1); |
| |
| float3 unit_light_vec = normalize( LightPos - Input.WrldPos ); |
| float dist_light_pos = distance( LightPos, Input.WrldPos ); |
| |
| // Work out phong shade |
| float light_vec_norm = dot( unit_light_vec, Input.Normal ); |
| float angle = clamp( light_vec_norm, 0, 1 ); |
| |
| float4 vertex_intensity = LightCol * angle; |
| |
| float4 diffuse = Input.Color * vertex_intensity; |
| |
| float3 reflection1 = ( Input.Normal * light_vec_norm * 2.0f ) - unit_light_vec; |
| float3 reflection = normalize( reflection1 ); |
| |
| float intensity = dot( reflection, unit_view_vec ); |
| if( intensity < 0 ) |
| { |
| intensity = 0; |
| } |
| |
| float spec1 = pow( intensity, 128.0f ); |
| float4 spec2 = float4(1,1,1,1) * spec1; |
| float4 specular = spec2 * LightCol; |
| |
| Output.Color += diffuse + specular; |
| Output.Color.a = 1.0f; |
| |
| return Output; |
| } |
| |
| technique Simplest |
| { |
| pass Pass0 |
| { |
| VertexShader = compile vs_3_0 SimplestVertexShader(); |
| PixelShader = compile ps_3_0 OurFirstPixelShader(); |
| } |
| } |
I hope this shows where i've done the mistake.
Ankur
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
If your materials have colors, then you need to extract those colors from the material properties, and configure them on your shader. Your shader currently doesn't even have material property parameters, so how could it color the materials?
Also, material color doesn't show up in the vertex color, so you should remove that channel.
Finally, I don't see you define LightColor anywhere. If it is defined, you can pre-multiply material color by light color for each modelmeshpart, and set that as the light color, and it will do the same thing as implementing a separate material color parameter.
Jon Watte, Direct3D MVP
kW X-port 3ds Max .X exporter
kW Animation source code
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
Hi,
The models i am loading in do have a material, in fact they have multiple materials for the same mesh (see my above post for more details). I've purposely left out the materials for now since i don't know how to extract the material properties from the .x file. How would i do that because then this would solve the problem.
Thanks
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
Ack, the post was just getting to the part I was looking for: how to access material data from the model. I've been messing with the BasicEffect code released and trying to implement a custom shader that can handle non-textured models but have been unable to find a way to get to the material data from the model (say, the diffuse color, specifically). I anyone could explain that to me I'd be very grateful. Thanks.
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
This is done inside the Content Pipeline - the MaterialContent contains all the data you need. See the Custom Model Effect sample (on this site) for an example of how to pull that information out into whatever effect you want to render with.
XNA Framework Developer -
blog - homepage
|
|
-
|
|
Re: Custom Effect not working properly with .x model
|
how to access material data from the model
As Shawn said, this is done inside the content processor. You have the MeshMaterialContent, and can examine that as much as you want. You can also add to the Tag property of the mesh information about w | | |