vertex shader help

Started by
12 comments, last by iota1410 19 years, 5 months ago
i have followed msdn's vertex shader tutorials and been able to successfully compile my code. i am using two buffers. one with x,y,z,rhw and another with color data. when i run it, however, the window pops up, but the picture doesn't show up. i think that my .vsh file might not be correct. if anyone has any examples they could share, i would really appreciate it. here is what mine looks like right now: ------------------- vs_2_0 dcl_position v0 dcl_color v1 mov oPos, v0 mov oD0, v1 ------------------- my render function contains: IDirect3DDevice9_SetVertexDeclaration(g_pd3dDevice, m_pVertexDeclaration ); IDirect3DDevice9_SetVertexShader(g_pd3dDevice, m_pVertexShader ); IDirect3DDevice9_SetStreamSource(g_pd3dDevice, 0, g_pV, 0, sizeof(struct vertex) ); IDirect3DDevice9_SetStreamSource(g_pd3dDevice, 1, g_pC, 0, sizeof(struct pixel) ); IDirect3DDevice9_DrawPrimitive(g_pd3dDevice, D3DPT_TRIANGLELIST, 0, 1 ); in the end nothing is draw in my window. [Edited by - iota1410 on November 9, 2004 2:39:04 PM]
Advertisement
what result did the example state? looking at your code, all it does is copy the input pos into the output register. not sure what that last line accomplishes, looks like a typo. it should be:

mov oD0, v1

this will copy the input color into the output diffuse register.
it was a typo, it should have been

mov oD0, v1

I want to draw a triangle at the position in the vertex buffer, using the colors in the color buffer. The position of my vertices never changes, only their colors. The hope is all I have to do is update my color buffer and then render it to the screen.

Currently all I get is my blue background.

I can get my triangle to appear using the FVF, but I would like to try using a shader.

alright so the shader itself is fine. you only need one stream source. so why this line:

IDirect3DDevice9_SetStreamSource(g_pd3dDevice, 1, g_pC, 0, sizeof(struct pixel) );

not sure what is happening there. Also make sure your vertex declaration is properly set and that you are running in DirectX debug mode D3D_DEBUG_INFO (something like that).
The way I understood streams, the first stream is the vertex buffer with the position info, the second stream is the color info. I got the code off of the Directx SDK. But they never show how the buffers were built in that particular case. Any Ideas?

Double check your vertex declaration. Also you can get the vsh compile errors at run time using this

	// Create a temp buffer for shader debugging	LPD3DXBUFFER err;	D3DXCreateBuffer(1024, &err);	//Load effect file	if(FAILED(D3DXCreateEffectFromFile(m_pd3dDevice, "vs_terrain.vsh", 	                NULL, NULL, 0, NULL, &m_fxTerrain, &err )))	{		char error[1024];		memcpy(error, err->GetBufferPointer(), 1024);		MessageBox(NULL, error, "Error", 0);		return E_FAIL;	}
No bombs, No guns, just an army of game creators...
My declarations are as follows:

#define D3DFVF_VERTEX (D3DFVF_XYZRHW)
#define D3DFVF_PIXEL (D3DFVF_DIFFUSE)
...
...
...
if( FAILED( IDirect3DDevice9_CreateVertexBuffer(g_pd3dDevice, 3*sizeof(struct vertex), 0, D3DFVF_VERTEX, D3DPOOL_DEFAULT, &g_pV, NULL ) ) )
{
return E_FAIL;
}

if( FAILED( IDirect3DDevice9_CreateVertexBuffer(g_pd3dDevice, 3*sizeof(struct pixel), 0, D3DFVF_PIXEL, D3DPOOL_DEFAULT, &g_pC, NULL ) ) )
{
return E_FAIL;
}

pixel only contains a color value and vertex contains the position data.
When combining streams using a vertex shader, you need to order the data in a way that can be pushed through the pipeline and taken apart by your shader. You can use a Vertex Declaration to do this.

This example shows how to combine a stream of height and normal values with a stream of x and z verts with texture coords

static D3DVERTEXELEMENT9 vertex_description[] = {	{0, 0, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},	{0, 8, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},	{0, 16,D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},	{1, 0, D3DDECLTYPE_FLOAT1, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 1},	{1, 4, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_NORMAL,   0},	D3DDECL_END()};


This is an example of how one is defined, but not a solution to your problem.

You then need to create a D3D object from the description

m_pd3dDevice->CreateVertexDeclaration(vertex_description, &vertex_dec)

Then your shader has to arange the input properly, like

struct VS_INPUT{	float2 Pos : POSITION0; 	float2 UV  : TEXCOORD0;	float2 UV2 : TEXCOORD1;	float YPos : POSITION1;	float3 norm: NORMAL0;};



I would give a more useful example implementation but i don't know off the top of my head if it would be correct. The SDK has an average tutorial on this, but there are some really good old Gamedev threads that you can use.

No bombs, No guns, just an army of game creators...
I use the following declaration. I got the code from the SDKs.

D3DVERTEXELEMENT9 decl[] = {
{ 0, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0 },
{ 1, 0, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT,D3DDECLUSAGE_COLOR, 0 },
D3DDECL_END()};

IDirect3DDevice9_CreateVertexDeclaration(g_pd3dDevice, decl, &m_pVertexDeclaration );

What else am I missing? I really thaought this would be simple. I am not even trying to manipulate the data at this point.
that vertex declaration doesn't look right. 4 floats are 16 bytes so:

D3DVERTEXELEMENT9 decl[] = {
{ 0, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0 },
{ 16, 0, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT,D3DDECLUSAGE_COLOR, 0 },
D3DDECL_END()};

This topic is closed to new replies.

Advertisement