'Simple' winding order issue

This topic is 2892 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

Recommended Posts

I have a box with vertices 0,1,2,3 such that my box looks like: 0-----1 | | 3-----2 My indices are listed as: 0,1,2, //first triangle 0,2,3 //second triangle As you can see both are listed in a clockwise winding order, however, only the first triangle is being drawn and the second is being culled. Rearranging the second triangle to 2,3,0 works, but I'm curious as to why 0,2,3 doesn't... both are clockwise.. Thanks [Edited by - Cailen on February 18, 2010 8:05:42 PM]

Share on other sites
I'm going to guess you're using a triangle strip, in which case I believe the winding order is reversed for each new triangle added to the strip.

Share on other sites
NO! That was actually the first thing I checked... happened in a previous program

Share on other sites
Any other ideas? This is boggling my mind... I am right in assuming that triangle with a clockwise winding order should not be culled in direct3d yes?

Share on other sites
Could you post the code you're using to draw them? It might be another issue (Not supplying the last vertex, passing in too few primitive, etc).

Share on other sites
Here is my vertex and index list:
[source lang=cpp] void TetrisBlock::init(ID3D10Device *device){	md3dDevice = device;	mNumVertices = 4;	mNumFaces = 2;	//create vertex buffer  - topleft corner = origin	Vertex vertices[] = 	{		{D3DXVECTOR3(0.0f,0.0f,0.0f)},         //top left          0        1		{D3DXVECTOR3(1.0f,0.0f,0.0f)},      //top right		{D3DXVECTOR3(1.0f,-1.0f,0.0f)},  //bottom right		{D3DXVECTOR3(0.0f,-1.0f,0.0f)}	  // bottom left           3        2	};	D3D10_BUFFER_DESC VertexBufferDesc;	VertexBufferDesc.Usage = D3D10_USAGE_IMMUTABLE;	VertexBufferDesc.ByteWidth = sizeof(Vertex)*mNumVertices;	VertexBufferDesc.BindFlags = D3D10_BIND_VERTEX_BUFFER;	VertexBufferDesc.CPUAccessFlags = 0; VertexBufferDesc.MiscFlags = 0;	D3D10_SUBRESOURCE_DATA VertexInitData;	VertexInitData.pSysMem = vertices;	HR(md3dDevice->CreateBuffer(&VertexBufferDesc,&VertexInitData,&mVertexBuffer));	//create index buffer	DWORD indices[] = 	{		0,1,2,		2,3,0	};	D3D10_BUFFER_DESC IndexBufferDesc;	IndexBufferDesc.Usage = D3D10_USAGE_IMMUTABLE;	IndexBufferDesc.ByteWidth = sizeof(DWORD)*mNumFaces*3;	IndexBufferDesc.BindFlags = D3D10_BIND_VERTEX_BUFFER;	IndexBufferDesc.CPUAccessFlags = 0; IndexBufferDesc.MiscFlags = 0;	D3D10_SUBRESOURCE_DATA IndexInitData;	IndexInitData.pSysMem = indices;	HR(md3dDevice->CreateBuffer(&IndexBufferDesc,&IndexInitData,&mIndexBuffer));}

And here is my code to draw the square:

[source lang=cpp]void TetrisBlock::draw(){	UINT stride = sizeof(Vertex);	UINT offset = 0;	md3dDevice->IASetVertexBuffers(0,1,&mVertexBuffer,&stride,&offset);	md3dDevice->IASetIndexBuffer(mIndexBuffer,DXGI_FORMAT_R32_UINT,0);	md3dDevice->DrawIndexed((mNumFaces*3),0,0);}

AND here is my code to render the scene:

[source lang=cpp]void Tetris::drawScene(){	D3DApp::drawScene();	md3dDevice->OMSetDepthStencilState(0,0);	float BlendFactors[] = {0.0f,0.0f,0.0f,0.0f};	md3dDevice->OMSetBlendState(0,BlendFactors,0xffffffff);	md3dDevice->IASetInputLayout(mVertexLayout);	md3dDevice->IASetPrimitiveTopology(D3D10_PRIMITIVE_TOPOLOGY_TRIANGLELIST);	//draw	D3D10_TECHNIQUE_DESC TechniqueDesc;	mTech->GetDesc(&TechniqueDesc);	for (UINT p = 0; p < TechniqueDesc.Passes; p++)		        {	mTech->GetPassByIndex(p)->Apply(0);			mTetrisBlock.draw();	}	mSwapChain->Present(0,0);}

Share on other sites
So... Is there nothing wrong with this?

Share on other sites
I'm not very familiar with d3d10 myself, but it may be that the SetPrimitiveTopology call applies only to Draw() calls and not DrawIndexed.

If you want to specifiy triangles, rather than a trianglestrip, your indices need to be:

0, 1, 2, 0xffffffff,
0, 2, 3

and call DrawIndexed( numFaces*3 + 1, 0, 0 );

DrawIndexed apparently expects a trianglestrip. The 0xffffffff (DWORD max value) is a break that indicates the winding order should be reset after (0,1,2) is drawn.

See Strip Cut Index in this link.

Another possibility, use just the 6 indices (no breaks) and call SetPrimitiveTopology after you bind the vertex and index buffers.

I.e.
SetVertexBuffers()
SetIndexBuffers()
SetPrimitiveTopology()

Share on other sites
I don't know anything about DirectX so this might not be a problem, but shouldn't you be using D3D10_BIND_INDEX_BUFFER instead of D3D10_BIND_VERTEX_BUFFER for the bind flags when creating your index buffer?

Share on other sites
AHHHH Yes the problem was a typo... THANK YOU!!