Getting adjacency data from a ID3DXBuffer(D3DXLoadMeshFromX( ))

Started by
11 comments, last by xissburg 18 years, 7 months ago
The definition of D3DXLoadMeshFromX():

HRESULT D3DXLoadMeshFromX(
  LPSTR pFilename,
  DWORD Options,
  LPDIRECT3DDEVICE8 pDevice,
  LPD3DXBUFFER* ppAdjacency,
  LPD3DXBUFFER* ppMaterials,
  PDWORD pNumMaterials,
  LPD3DXMESH* ppMesh
);
Well, I want to work with the ppAdjacency data.To get it is just set the address of a ID3DXBuffer.According to the DX documentation: ppAdjacency [out] Address of a pointer to an ID3DXBuffer interface. When the method returns, this parameter is filled with an array of three DWORDs per face that specify the three neighbors for each face in the mesh. So, I create a DWORD and use the ID3DXBuffer->GetBufferPointer().But I don't know how to interpret the data into the DWORD!!!How to do it?!?please teach me...I'm needing it a lot.... Thanks
.
Advertisement
(DWORD*)buffer->GetBufferPtr();
:P

This is what I do...

DWORD* Adjacency = (DWORD*)AdjacencyBuffer->GetBufferPointer();

I know how to get the adjacency data but I dont know how to interpret it.I read the DWORD values I get as Adjacency[7] but I dont know what the number inside of it means...Do you know it?
.
The idea is that since a triangle has three sides, it can have 3 other triangles neighboring it. The adjacency array contains this information. The data contained in this array are merely face indices.

Each face of the triangle has 3 slots in the adjacency array that correspond to it. Face 0 corresponds to slots 0-2, face 1 corresponds to slots 3-5, and so on.

So say you wanted to find which triangles were neghboring face 5 in your mesh. Since each face is neighbored by 3 other faces, each of which are indicated by a slot in the adjacency array, then the neighbors of face 3 are accesed like this:
dwFace = 5;// Multiply by 3 because there are 3 neighboring triangles for each face.dwNeighbor0 = pAdjacencyTable[dwFace * 3 + 0];  // First face neighboring triangle specified by dwFacedwNeighbor1 = pAdjacencyTable[dwFace * 3 + 2];  // Second face neighboring triangle specified by dwFace dwNeighbor2 = pAdjacencyTable[dwFace * 3 + 2];  // Third face neighboring triangle specified by dwFace

Say you wanted to access the vertices of the second face of the original triangle, you would do something like this:
// dwNeighbor* are the face indices.  to access their vertices, we multiply by 3 because there are 3 vertices per face.v0 = pVertices[pIndices[dwNeighbor1*3 + 0]];v1 = pVertices[pIndices[dwNeighbor1*3 + 1]];v1 = pVertices[pIndices[dwNeighbor1*3 + 2]];

Hope this helps,
neneboricua
hmm...I understood it a bit but, I'm not sure if it will work...to help you understand my situation, this is my simple 'test terrain' in a wire frame top view and its vertex indices:



As you can see, the vertex indices have a strange flow...The terrain was created into 3dsmax and then exported to .x.I dont know anything into 3dsmax which can change the vertex indices...wow...this task is really hard...

How can I get it?!? :(
.
Well, accessing the adjacency buffer has been explained and if you're not sure about part of that explanation, you can ask and we can try to clear it up.

However, what is it exactly that you're trying to do? I see the image about how the vertices of your terrain are organized and eventhough its a bit unconventional, there's nothing really weird about it. Are you trying to do something to each of the individual vertices? Are you trying to perform some operation on each triangle in the mesh? What is it that you're trying to do?

neneboricua
Thanks for your answers man.

About the method you've described, I understood the way to work with the ajacency data and I got it into my application. Well, it works correctly but, what I really want is to get all the vertex positions for each triangle putting them into an array of this structure:

struct TRIANGLE{    D3DXVECTOR3 v0; //vertex 0    D3DXVECTOR3 v1; //vertex 1    D3DXVECTOR3 v2; //vertex 2    D3DXVECTOR3 N;  //triangle normal vector    float       d;  //triangle plane distance form origin(used in the plane equation)};...//then I can do something like this:TRIANGLE* Triangle = new TRIANGLE[TerrainMesh->GetNumFaces()];//where TerrainMesh is a pointer to a ID3DXMesh interface with the my terrain loaded


I'll use it to detect collisions with the terrain so I need the triangles properties to do it...

I hope yoou understood and I also hope you can help me because I'm really needing to know it man....

Thank you a lot...
.
lets just say you did something like this... just add a constructor to your struct for convenience...

struct TRIANGLE{    D3DXVECTOR3 v0; //vertex 0    D3DXVECTOR3 v1; //vertex 1    D3DXVECTOR3 v2; //vertex 2    D3DXVECTOR3 N;  //triangle normal vector    float       d;  //triangle plane distance form origin(used in the plane equation)        TRIANGLE::TRIANGLE(const D3DXVECTOR3& v0_,const D3DXVECTOR3& v0_,const D3DXVECTOR3& v0_, const D3DXVECTOR3& n_)    :v0(v0_),v1(v1_)v2(v2_),N(n_),d(?)    {}    }

the adjacency buffer is a DWORD array? then u could just iterate through it saving all the data to a vector of your TRIANGLE struct... something like this... might be ugly but just a quick example of how you could do it....


//point to endvoid* end = &pAdjacencyTable[0] plus (sizeof(pAdjacencyTable)/sizeof(*pAdjacencyTable)); //point to startvoid* it = &pAdjacencyTable[0];while(it != end){  // get every 3 values to make up the vector   //float a = float(*it);  //increment (it)  //float b = float(*it);  //increment (it)  //float c = float(*it);  //increment (it)  //store values into a d3dvector3  //D3DXVECTOR3 v0 ( a , b , c );  // do the same for 2 more vectors  //D3DXVECTOR3 v1 ( a , b , c );  // ...  // ...  //D3DXVECTOR3 v2 ( a , b , c );  // ...  // ...  //store data  //vTRIANGLES.push_back(TRIANGLE(v0,v1,v2,normal));}...


ugly code but just tryin to give an idea... u would have a
vector of TRIANGLE structs with all the data ... just iterate through saving all the data...
lol...sorry but I didnt understand you... :(
Well, yesterday I was not too much inspired to write my reply but now I'll explain it better...

I already know a method to get all the vertex positions from my 'TerrainMesh' (ID3DXMesh pointer).It works perfectly.No problems within it. What I want to do now is to associate the vertex indices with each vertex of each triangle for example, looking at the top view of my simple terrain and thinking that the triangle index increases form left to right and from top to bottom:

//Associate the vertex indices with the triangles vertexTriangle[0] = {Vertex[4], Vertex[3], Vertex[9], D3DXVECTOR3(0.0f, 0.0f, 0.0f), 0.0f};Triangle[1] = {Vertex[3], Vertex[8], Vertex[9], D3DXVECTOR3(0.0f, 0.0f, 0.0f), 0.0f};//and so on...


Vertex is a D3DXVECTOR3 array which has all the vertex positions stored.The number inside the [] is the vertex index. Did you understand it now?!?

I don't know if using adjacency data I can get it but, I'm really trying to find any method to do it...If you know any, please tell me man!!

Thanks for all
.
ok i see what you mean now... you need some algorithm for that... maybe something like this?

	int totalVertices = 25;	int verticesPerRow = sqrt(totalVertices);	int counter = 0;	int ndx = 0;	int size =  totalVertices - verticesPerRow - 1;	int upperVertex = 0;	int lowerVertex = verticesPerRow;	while(counter != size)	{		/*get upper left triangle in the square*/		//Triangle[ndx] = TRIANGLE( Vertex[upperVertex] , Vertex[lowerVertex plus 1] , Vertex[upperVertex plus 1] );		//increment ndx;		/*get lower right triangle in the square*/		//Triangle[ndx] = TRIANGLE( Vertex[upperVertex] , Vertex[lowerVertex] , Vertex[lowerVertex plus 1] );		//increment ndx;		//increment upperVertex;		//increment lowerVertex;		//increment counter;	}

thats the basic idea


I remember doing something like this when i made a grid... get each square storing both triangles each time


but that would make Triangle[0] start with Vertex[0] ( the upper right corner )... if you wanted it to start from Vertex[4] ( the upper left corner ) then you would have make the index equal to a multiple of the verticesPreRow then decrement it each time through the loop... i think

This topic is closed to new replies.

Advertisement