?/TD> |
Microsoft DirectX 9.0 |
Conceptually, the vertex declaration is a way of programming the vertex direct memory access (DMA) and the tessellator engine of the graphics pipe. It expresses the data layout and the tessellator operations concisely. To address the complexity and extensibility of declarations in Microsoft?DirectX?8.x, a new format for expressing vertex streams has been introduced.
Vertex shaders and vertex declarations are no longer bound together at CreateVertexShader time. The shader validation has been divided into two parts. One runs at the vertex shader creation time and the other runs at the DrawPrimitive time. Vertex shaders and vertex declarations are represented by objects.
Decls are no longer expressed as streams of DWORDs. They are expressed as an array of D3DVERTEXELEMENT9 structures. Each element of the array describes one vertex element.
Additionally, to address application programming interface (API) usability issues, there will be a separate SetFVF call that is equivalent to the SetVertexDeclaration call. This is a convenience function; when this call is made, it will clobber the currently set declaration and vice versa. If the driver is pre-DirectX 8.0 (NumStreams is set to 0), SetVertexDeclaration might fail for declarations that cannot be converted to flexible vertex format (FVF) with an error. SetFVF can be used with both the fixed function, as well as the programmable vertex pipeline. Internally, FVF is converted to a vertex shader declaration using the Mapping FVF to DirectX 9.0 Decl. DCL commands in vertex shader functions should be written with this in mind. Because of this conversion, all further discussion will be about vertex declarations only.
The following are the fields in the D3DVERTEXELEMENT9 structure and their explanations.
The following are the allowed.
Semantics, usage index | Special interpretations |
---|---|
(D3DDECLUSAGE_POSITION, 0 ) | Untransformed position in the fixed function vertex shader and the N-patch tessellator. |
(D3DDECLUSAGE_POSITION, 1) | Untransformed position in the fixed function vertex shader for skinning. |
(D3DDECLUSAGE_BLENDWEIGHT, 0) | Blend weights in the fixed function vertex shader. |
(D3DDECLUSAGE_BLENDINDICES, 0) | Matrix indices for the fixed function vertex-shader-indexed paletted skinning. |
(D3DDECLUSAGE_NORMAL, 0) | Vertex normal in the fixed function vertex shader and the N-patch tessellator. |
(D3DDECLUSAGE_NORMAL, 1) | Vertex normal in the fixed function vertex shader for skinning. |
(D3DDECLUSAGE_PSIZE, 0) | Point-size attribute that is used by the setup engine of the rasterizer to expand a point into a quad for the point-sprite functionality. |
(D3DDECLUSAGE_TEXCOORD, n) | Texture coordinates in fixed function vertex shader and pre-3_0 pixel shader. These can be used to pass user defined data. |
(D3DDECLUSAGE_TANGENT, n) | Tangent. It has no special interpretation. |
(D3DDECLUSAGE_BINORMAL, n) | Binormal. It has no special interpretation. |
(D3DDECLUSAGE_TESSFACTOR, 0) | Tessellation factor that is used in the tessellation unit to control the rate of tessellation. |
(D3DDECLUSAGE_POSITIONT, 0) | Post-transformed position. When a declaration containing this is set, it bypasses the vertex processing. |
(D3DDECLUSAGE_COLOR, 0) | Diffuse color in the fixed function vertex shader and pre-3_0 pixel shader. |
(D3DDECLUSAGE_COLOR, 1) | Specular color in the fixed function vertex shader and pre-3_0 pixel shader. |
(D3DDECLUSAGE_FOG, 0) | Fog blend value, that is used post pixel shader when a pre-3_0 pixel shader is set. |
(D3DDECLUSAGE_DEPTH, n) | Depth. It has no special interpretation. |
(D3DDECLUSAGE_SAMPLE, n) | Displacement value looked up. It can be used only with D3DDECLMETHOD_LOOKUPPRESAMPLED or D3DDECLMETHOD_LOOKUP. |
A special value for the vertex element is considered the end of vertex shader declaration. This value is #define D3DDECL_END() {0xFF,0,0,0,0,0}.
UsageIndex is used in conjunction with Usage to specify the semantic of a vertex element. Instead of using D3DVSDE_POSITION2 as in DirectX 8.x, now user can specify D3DDECLUSAGE_POSITION as Usage and UsageIndex = 1.
A Decl specifies the input to the tessellator engine (or directly the vertex processing engine in case the tessellator is not used) as well as its output. The type field in the vertex element specifies the type of the input data to the decl. The output type is implied by the method.
There is a preamble in the vertex shader that has the form of {semantic, semantic index, register number}. The runtime matches up the declaration's semantic with the shader's semantic information, thus pairing up an input register with byte offset into a stream.
FVF | Data type | Usage | Usage index |
---|---|---|---|
D3DFVF_XYZ | D3DDECLTYPE_FLOAT3 | D3DDECLUSAGE_POSITION | 0 |
D3DFVF_XYZRHW | D3DDECLTYPE_FLOAT4 | D3DDECLUSAGE_POSITIONT | 0 |
D3DFVF_XYZW | D3DDECLTYPE_FLOAT4 | D3DDECLUSAGE_POSITION | 0 |
D3DFVF_XYZB5 and D3DFVF_LASTBETA_UBYTE4 | D3DVSDT_FLOAT3 D3DVSDT_FLOAT4 D3DVSDT_UBYTE4 | D3DDECLUSAGE_POSITION D3DDECLUSAGE_BLENDWEIGHT D3DDECLUSAGE_BLENDINDICES | 0 |
D3DFVF_XYZB5 and D3DFVF_LASTBETA_D3DCOLOR | D3DVSDT_FLOAT3 D3DVSDT_FLOAT4 D3DVSDT_D3DCOLOR | D3DDECLUSAGE_POSITION D3DDECLUSAGE_BLENDWEIGHT D3DDECLUSAGE_BLENDINDICES | 0 |
D3DFVF_XYZB5 | D3DDECLTYPE_FLOAT3 D3DDECLTYPE_FLOAT4 D3DDECLTYPE_FLOAT1 | D3DDECLUSAGE_POSITION D3DDECLUSAGE_BLENDWEIGHT D3DDECLUSAGE_BLENDINDICES | 0 |
D3DFVF_XYZBn (n=1..4) | D3DDECLTYPE_FLOAT3 D3DDECLTYPE_FLOATn | D3DDECLUSAGE_POSITION D3DDECLUSAGE_BLENDWEIGHT | 0 |
D3DFVF_XYZBn (n=1..4) and D3DFVF_LASTBETA_UBYTE4 | D3DDECLTYPE_FLOAT3 D3DDECLTYPE_FLOAT(n-1) D3DDECLTYPE_UBYTE4 | D3DDECLUSAGE_POSITION D3DDECLUSAGE_BLENDWEIGHT D3DDECLUSAGE_BLENDINDICES | 0 |
D3DFVF_XYZBn (n=1..4) and D3DFVF_LASTBETA_D3DCOLOR | D3DDECLTYPE_FLOAT3 D3DDECLTYPE_FLOAT(n-1) D3DDECLTYPE_D3DCOLOR | D3DDECLUSAGE_POSITION D3DDECLUSAGE_BLENDWEIGHT D3DDECLUSAGE_BLENDINDICES | 0 |
D3DFVF_NORMAL | D3DDECLTYPE_FLOAT3 | D3DDECLUSAGE_NORMAL | 0 |
D3DFVF_PSIZE | D3DDECLTYPE_FLOAT1 | D3DDECLUSAGE_PSIZE | 0 |
D3DFVF_DIFFUSE | D3DDECLTYPE_D3DCOLOR | D3DDECLUSAGE_COLOR | 0 |
D3DFVF_SPECULAR | D3DDECLTYPE_D3DCOLOR | D3DDECLUSAGE_COLOR | 1 |
D3DFVF_TEXCOORDSIZEm(n) | D3DDECLTYPE_FLOATm | D3DDECLUSAGE_TEXCOORD | n |
Presence of a vertex element with (D3DUSAGE_POSITIONT, 0) is used to indicate to the device that the vertex data coming in has already been through vertex processing (like an FVF with D3DFVF_XYZRHW bit set). At Draw time, if the currently set declaration has an element with the (D3DUSAGE_POSITIONT, 0) semantic, the entire vertex processing is skipped (just as if an FVF with D3DFVF_XYZRHW bit has been set).
There are some restrictions on vertex declarations with (D3DDECLUSAGE_POSITIONT, 0):
In addition, there are some restrictions on such declaration, related to the device driver version. These restrictions are in effect because Direct3D sends such declarations directly to the driver without doing any conversion.
More general declarations are allowed.
Runtime validates the creation of declarations. Following are the general rules for what declarations are legal.
There are additional restrictions when using with hardware vertex processing on a DirectX 8.x driver :
The CreateVertexDeclaration might fail if the declaration provided cannot be converted to a DirectX 8.x-style decl. For mixed mode device this failure will happen at Draw* time because that is the only time it can be known whether this shader is being used with hardware or software vertex processing.
Only declarations that adhere to the following rules can be used:
When a declaration is used with hardware vertex processing on a DirectX 8.x driver, the Direct3D runtime converts it to a DirectX 8.x-style declaration with the following rules.
DirectX 9.0 Usage | DirectX 9.0 Usage Index | DirectX 8.0 |
---|---|---|
D3DDECLUSAGE_POSITION | 0 | D3DVSDE_POSITION |
D3DDECLUSAGE_POSITION | 1 | D3DVSDE_POSITION2 |
D3DDECLUSAGE_NORMAL | 0 | D3DVSDE_NORMAL |
D3DDECLUSAGE_NORMAL | 1 | D3DVSDE_NORMAL2 |
D3DDECLUSAGE_BLENDWEIGHT | 0 | D3DVSDE_BLENDWEIGHT |
D3DDECLUSAGE_BLENDINDICES | 0 | D3DVSDE_BLENDINDICES |
D3DDECLUSAGE_PSIZE | 0 | D3DVSDE_PSIZE |
D3DDECLUSAGE_COLOR | 0 | D3DVSDE_DIFFUSE |
D3DDECLUSAGE_COLOR | 1 | D3DVSDE_SPECULAR |
D3DDECLUSAGE_TEXCOORD | n | D3DVSDE_TEXCOORDn |
When a declaration is used with hardware vertex processing on a DirectX 7.0 driver, the Direct3D runtime converts it to an FVF with the following rules.
Data type | Usage | Usage index | FVF |
---|---|---|---|
D3DDECLTYPE_FLOAT3 | D3DDECLUSAGE_POSITION | 0 | D3DFVF_XYZ |
D3DDECLTYPE_FLOAT4 | D3DDECLUSAGE_POSITIONT | 0 | D3DFVF_XYZRHW |
D3DDECLTYPE_FLOATn | D3DDECLUSAGE_BLENDWEIGHT | 0 | D3DFVF_XYZBn |
D3DDECLTYPE_UBYTE4 | D3DDECLUSAGE_BLENDINDICES | 0 | D3DFVF_XYZB (nWeights+1) |
D3DDECLTYPE_FLOAT3 | D3DDECLUSAGE_NORMAL | 0 | D3DFVF_NORMAL |
D3DDECLTYPE_FLOAT1 | D3DDECLUSAGE_PSIZE | 0 | D3DFVF_PSIZE |
D3DDECLTYPE_D3DCOLOR | D3DDECLUSAGE_COLOR | 0 | D3DFVF_DIFFUSE |
D3DDECLTYPE_D3DCOLOR | D3DDECLUSAGE_COLOR | 1 | D3DFVF_SPECULAR |
D3DDECLTYPE_FLOATm | D3DDECLUSAGE_TEXCOORD | n | D3DFVF_TEXCOORDSIZEm(n) |
D3DDECLTYPE_FLOAT3 | D3DDECLUSAGE_POSITION | 1 | N/A |
D3DDECLTYPE_FLOAT3 | D3DDECLUSAGE_NORMAL | 1 | N/A |
A vertex declaration could be used to describe the output of ProcessVertices. Such declaration should adhere to the following rules.