Sign in to follow this  

How to retrieve a vertex buffer stream?

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

If you intended to correct an error in the post then please contact us.

Recommended Posts

rcMeshLoaderX::rcMeshLoaderX(CMesh *mesh) {
    LPDIRECT3DVERTEXBUFFER9 vb;
    LPDIRECT3DINDEXBUFFER9 ib;
    void *pVertices;
    LPD3DXMESH geom = mesh->GetStaticMesh();
    geom->GetVertexBuffer(&vb);
    geom->GetIndexBuffer(&ib);

    VOID* pVertices;

    if(FAILED(vb->Lock(0, sizeof(???),
            (BYTE**)&pVertices, 0 ) ) )
        return E_FAIL;

    memcpy(pVertices, g_Vertices, sizeof(g_Vertices));
    vb->Unlock();

    
}

CMesh * contains the actual mesh that is loaded from the .X file.

Now I want to dismantle this structure and convert to a vertex buffer stream.

Any ideas how?

Thanks

Jack

Share this post


Link to post
Share on other sites


convert to a vertex buffer stream

 

It's not clear what you actually want to do. If you mean to use it, for example, in a SetStreamSource call, have you tried using the vertex buffer as you access it in the code you posted?

 

That is, it appears LPDIRECT3DVERTEXBUFFER9 vb is the address of the vertex buffer data after you call GetVertexBuffer.

 

If that's not what you mean, you'll have to provide additional information - e.g., what is CMesh? What is it's structure, etc.?

Share this post


Link to post
Share on other sites
I'd like to build a navigation mesh based on the geometry
class CMesh
{
public:
	CMesh(void);
	~CMesh(void);

	bool Load(LPDIRECT3DDEVICE9 pDevice, char *pFilename, bool bVertexBlending = false);
	void SaveHierarchyToFile();
	bool IsVertexBlending()		{ return m_bEnableVertexBlending; }	

	LPD3DXMESH GetStaticMesh() 	{ return m_pStaticMesh; }

	// frame root and animation controller
	LPD3DXFRAME					GetFrameRoot()		{ return m_pFrameRoot; }
	LPD3DXANIMATIONCONTROLLER   GetAnimController() { return m_pAnimController; }

	// bounding volume 
	D3DXVECTOR3 GetCenter() { return m_vSphereCenter; }
	float		GetRadius() { return m_fSphereRadius; }
	void		GetBox(D3DXVECTOR3 *vMin, D3DXVECTOR3 *vMax) { *vMin = m_vBoxMin; *vMax = m_vBoxMax; }

	LPD3DXMESH GetBoxMesh()		{ return m_pBoundingBox; }
	LPD3DXMESH GetSphereMesh()	{ return m_pBoundingSphere; }

private:
	void PrintFrame(D3DXFRAME *pCurFrame);	
	bool GenerateSkinnedMesh(LPD3DXFRAME pCurFrame);
	bool MapFramesToBones(LPD3DXFRAME pCurFrame);	
	bool InitBounds();

private:
	LPDIRECT3DDEVICE9 m_pDevice;
	
	bool m_bEnableVertexBlending;

	LPD3DXFRAME					m_pFrameRoot;
	LPD3DXANIMATIONCONTROLLER	m_pAnimController;
	
	LPD3DXMESH					m_pStaticMesh;

	DWORD						m_dwNumMeshes;

	// bounding volume properties
	LPD3DXMESH	m_pBoundingBox;
	LPD3DXMESH	m_pBoundingSphere;	
	D3DXVECTOR3 m_vBoxMin, m_vMind;
	D3DXVECTOR3 m_vBoxMax, m_vMaxd;
	D3DXVECTOR3 m_vSphereCenter, m_vCenterd;  // Center of bounding sphere of object
	float       m_fSphereRadius, m_fRadiusd;  // Radius of bounding sphere of object

	// miscellaneous
	string	 m_DebugString;
	char	 *m_pFilename;
};

Share this post


Link to post
Share on other sites

If you dont know vertex format, take the declaration from mesh like this:

auto dxMesh = GetStaticMesh();

D3DVERTEXELEMENT9 decl[MAXD3DDECLLENGTH];
dxMesh->GetDeclaration(decl);

WORD offsetToPosition = 0;

for (UINT i = 0; i < MAXD3DDECLLENGTH; ++i)
{
    if (D3DDECLUSAGE_POSITION == decl[i].Usage)
    {
        offsetToPosition = decl[i].Offset;
    }
}

DWORD vertStride = dxMesh->GetNumBytesPerVertex();
DWORD numVerts = dxMesh->GetNumVertices();
BYTE* pVert;
 
dxMesh->LockVertexBuffer(0, (LPVOID*)&pVert);
for (DWORD i = 0; i < numVerts; ++i)
{
    D3DXVECTOR3 currentPos = *(D3DXVECTOR3*)(&pVert[vertStride * i + offsetToPosition]);
    ...// do something
}
dxMesh->UnlockVertexBuffer();
Edited by belfegor

Share this post


Link to post
Share on other sites

If you are looking to do CPU-side processing on the mesh, it might be easier to use something like CloneMeshFVF to transform it into your own vertex format rather than working with whatever format the mesh was loaded in.

 

Highly likely that there will be vertex attributes only required for rendering that you wouldn't need for doing navmesh processing for example.

Share this post


Link to post
Share on other sites

Hello, belfegor, yes may I have your code please?

I am working hard to figure out why the index went exploded to a large number.

Maybe the Index Stride overflows the index buffer?!

Comments:

The index1 at the first iteration already went exploded so that the subsequent read on the

const float* v1 = &m_verts[m_tris[i+1]*3];

becomes undefined....

 

I will PM you.

Thanks

Jack

auto dxMesh = mesh->GetStaticMesh();

    D3DVERTEXELEMENT9 decl[MAXD3DDECLLENGTH];
    dxMesh->GetDeclaration(decl);

    WORD offsetToPosition = 0;

    for (UINT i = 0; i < MAXD3DDECLLENGTH; ++i)
    {
        if (D3DDECLUSAGE_POSITION == decl[i].Usage)
        {
            offsetToPosition = decl[i].Offset;
        }
    }


    // Get Vertex Information
    DWORD vertStride = dxMesh->GetNumBytesPerVertex();
    DWORD numVerts = dxMesh->GetNumVertices();
    
    DWORD indStride = sizeof(WORD);
    DWORD opt = dxMesh->GetOptions();
    if((opt & D3DXMESH_32BIT) == D3DXMESH_32BIT)
    {
        indStride = sizeof(DWORD);
    }
    BYTE* pIndices;    
    dxMesh->LockIndexBuffer(0, (LPVOID*)&pIndices);
    DWORD numInd = dxMesh->GetNumFaces() * 3;
    for(DWORD i = 0; i < numInd; i += 3)
    {
        int index0 = *(int*)(&pIndices[indStride * i + 0]);
        int index1 = *(int*)(&pIndices[indStride * i + 1]);
        int index2 = *(int*)(&pIndices[indStride * i + 2]);
        addTriangle(index0, index1, index2, tcap);
 
    }
Edited by lucky6969b

Share this post


Link to post
Share on other sites

I sort of revised the code, and wondering if that works.

    auto dxMesh = mesh->GetStaticMesh();    
    DWORD * pIndexList;
    dxMesh->LockIndexBuffer(D3DLOCK_READONLY | D3DLOCK_NOSYSLOCK,
        (void **)&pIndexList);

    DWORD numInd = dxMesh->GetNumFaces() * 3;

    for(DWORD i = 0; i < numInd; i += 3)
    {     
        int index0 = pIndexList[i+0];
        int index1 = pIndexList[i+1];
        int index2 = pIndexList[i+2];
        addTriangle(index0, index1, index2, tcap);
 
    }

    dxMesh->UnlockIndexBuffer();
     dxMesh->GetVertexBuffer(&vb);
    //get the number of vertices in the buffer

    DWORD vertStride = dxMesh->GetNumBytesPerVertex();
    int NumVertices = dxMesh->GetNumVertices();


    //get the vertex buffer description so we can determine the

    //size of a single vertex for the offset

    int offset;
    D3DVERTEXBUFFER_DESC desc;
    vb->GetDesc(&desc);
    offset=desc.Size/NumVertices;
    
    
    dxMesh->LockVertexBuffer(0, (LPVOID*)&pVert);   
    
    for (DWORD i = 0; i < NumVertices; ++i)
    {
        D3DXVECTOR3 currentPos = *(D3DXVECTOR3*)(&pVert[vertStride * i + offset]);     

        // vertices
        //x
        const float v0 = currentPos.x;
        //y
        const float v1 = currentPos.y;
        //z
        const float v2 = currentPos.z;

        addVertex(v0, v1, v2, vcap);
    }

Share this post


Link to post
Share on other sites

Yeah i see now that i f**** up with indexing into mesh indices.

 

In my code i used known vertex/index format so i had no problems. I rewrote it with this method and get it to work correctly this time.laugh.png

http://pastebin.com/EtYe1u3h# & http://pastebin.com/NaUzCkUM

 

Note: if your input mesh is with 32bit indices (vertex count > 65535) comment out buildDebugMesh() function or rewrite it to work for that kind.

I use it to build X mesh to be able to see what generated nav-mesh looks like.

Edited by belfegor

Share this post


Link to post
Share on other sites

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

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this