Terrain Texturing using Position, Color, Normal, and TEXTURE???

Started by
13 comments, last by vagos21 16 years, 9 months ago
I am stumped. I am using Managed DirectX 9 - C#. I have a heightmap terrain and have had some success applying color and texture to it using the CustomVertex.PostionColorTextured. However, is there any way to add a Normal attribute as well? I would like lighting to be applied to the terrain as well. It doesn't appear that DirectX supports a CustomVertex.PositionColorNormalTextured. I have tried to create my own VertexDeclaration to support this functionality - however I either get the texture or the color - but never both to appear properly. Thank you.
Advertisement
MDX offers such ready to use structures only for some common vertex formats. A vertex declaration is the right way to create your own custom vertex structure. There are some samples in the SDK (HDRFormats, HDRCubeMap or HLSLwithoutEffects) that show how it works.
I think I already know the answer to this, but...

When I create my own vertex declaration it is up to me to ensure that it is populated properly through a vertex shader? DirectX will not handle this?



The vertex declaration is responsible to transfer the values from your vertex buffer to the vertex shader input registers.
The Binding is done with the DeclarationUsage and UsageIndex on the vertex element side and with the Semantic on the shader side. I assume you use HLSL.

Example
VS_OUTPUT main( in float3 vPosition : POSITION,
in float2 tex: TEXCOORD )

The vertex declaration elements need to use the following Declaration Usage to bind these two inputs.
DeclarationUsage.Position
DeclarationUsage.TextureCoordinate
The UsageIndex would be 0 in both cases.

The UsageIndex is used if you want to bind multiple inputs with thze same usage
in float2 tex1: TEXCOORD1,
in float2 tex2: TEXCOORD2

You are still responsible to fill the vertex buffer in a way that matches to the vertex declaration. But you can create an own structure (not a class) for this purpose that work like the predefined.
I guess I was being a little naive in thinking DirectX "might" be able to interpret my vertex declaration. I was hoping to postpone learning HLSL - but I guess now is a good a time as any.

Thank you very much Demirug.
Well you don’t necessary need a vertex shader when you use a vertex declaration.

The declaration usages work with the fixed pipeline too. An element with the usage Position will be transformed by your matrices like it works with the predefined struts. The same is true for texture coordinates, colors, normals, etc. Therefore the fixed function pipeline will “interpret” your vertex declaration depending on the usage you set.

But learning HLSL is a good idea anyway. The MDX successor XNA Framework supports only the shader based model and with Direct3D 10 the ficed functions are removed even from the native API.
Well, I am defining the usages in the vertex declaration but DirectX is not interpreting it as I would have expected. Using the following I get a textured terrain without color.

I have tried changing the ordering of the VertextElements and all that seems to do is produce a colored terrain without texture.

public static readonly VertexElement[] Declarator = new VertexElement[]{new VertexElement(0, 0, DeclarationType.Float3,                                        DeclarationMethod.Default,                                        DeclarationUsage.Position, 0),                new VertexElement(0, 12, DeclarationType.Color,                                        DeclarationMethod.Default,                                        DeclarationUsage.Color, 0),                new VertexElement(0, 16, DeclarationType.Float3,                                         DeclarationMethod.Default,                                         DeclarationUsage.Normal, 0),                                                        new VertexElement(0, 28, DeclarationType.Float2,                                         DeclarationMethod.Default,                                         DeclarationUsage.TextureCoordinate, 0),                                                                                                                VertexElement.VertexDeclarationEnd                             };
Your vertex declaration looks fine for me.

Maybe your vertex stride is not correct and therefore you lost some parts of the vertex.

You should try to enable the Direct3D debug runtime. Can be done with the DirectX Control Panel. As you use managed DirectX you will need an external debug monitor or enable unmanaged debugging in your C# project to see the messages. This can give you often at least a hint what’s going wrong.
The Stride Size is built off of the vertex Declaration - so I don't think that is the problem.

I ran it in Debug Mode and the only thing returned were a bunch of D3D warnings about redundant render states.

HLSL is looking better and better to me. It sounds like I should learn it anyway...

            /// <summary>            /// The vertex stride size.            /// </summary>            public static readonly int StrideSize = VertexInformation.GetDeclarationVertexSize(Declarator, 0);


Quote:Original post by AtomicWedgie
I am stumped. I am using Managed DirectX 9 - C#. I have a heightmap terrain and have had some success applying color and texture to it using the CustomVertex.PostionColorTextured.

However, is there any way to add a Normal attribute as well? I would like lighting to be applied to the terrain as well.

It doesn't appear that DirectX supports a CustomVertex.PositionColorNormalTextured. I have tried to create my own VertexDeclaration to support this functionality - however I either get the texture or the color - but never both to appear properly.

Thank you.

You wouldn't normally use both colour and normal attributes. When a normal is used, the lighting (either fixed function or shader based) calculates a colour based on the light colour and object colour. This results in a diffuse (and potentially specular) colour, which is a direct replacement to specifying the colour in the vertex.

If you do want to use the per-vertex colour as the object colour, you'd have to write a shader that calculates the resulting colour from that.

This topic is closed to new replies.

Advertisement