Archived

This topic is now archived and is closed to further replies.

sherman

3DS Max R4.2 Exporter Plugin Texturing Problem

Recommended Posts

Dear all, It seems that I am still having problems with my 3D model importer and eignafx''s tip on drawing all the 3 vertices of all the faces in the model didn''t seem to help. So, if anybody knows how I can fix the problem, please tell me. Here is my Max 4.2 exporter code (all source code from here and output at the end): // Write basic mesh data (excluding bone data) to file. bool writeMeshData( INode* ptrINode, fstream& m_fsOutFile, ofstream* ofsTextFile ) { // If selected node is not valid and is not a mesh. if ((!ptrINode)||(!IsMesh(ptrINode))) { // Return failure. return false; } // Get transformation matrix for the selected mesh. Matrix3 tm = ptrINode->GetObjectTM(0); // Get the state of the selected mesh. ObjectState os = ptrINode->EvalWorldState(0); int iDummy; // Get a handle to the mesh. Mesh& mesh = *(( (GeomObject*) os.obj)-> GetRenderMesh(0,ptrINode,s_nullView,iDummy)); // Gets the current position in file. long lStartPosition = m_fsOutFile.tellg(); // Skip the mesh header section. m_fsOutFile.seekg( sizeof(StructS3DMesh), ios::cur); ///////////////////////////////////////////////////////////////// // Write StructS3DModelVertex ///////////////////////////////////////////////////////////////// ///// *ofsTextFile << "\n" << "[StructS3DModelVertex Section]" << "\n"; // Create a mesh header. StructS3DMesh structs3dmeshHeader; // Allocate memory for the mesh header. memset(&structs3dmeshHeader, 0, sizeof(StructS3DMesh)); // Get the mesh vertex count. structs3dmeshHeader.m_iS3dmodelvertexCount = mesh.getNumVerts(); // Get the offset in the file to the StructS3DModelVertex section. structs3dmeshHeader.m_lS3dmodelvertexOffset = m_fsOutFile.tellg(); // build the normals mesh.buildNormals(); // Loop through all the vertices for( int i = 0; i < structs3dmeshHeader.m_iS3dmodelvertexCount; i++ ) { // Get the vertex coordinates. // Remember to multiply by Max''s transformation matrix. Point3 pnt = mesh.getVert(i) * tm; // Get the vertex normals. Point3 norm = Normalize(mesh.getNormal(i)); // Get the vertex texture coordinates. UVVert uvTexCoordinates = getTextureUV(i, &mesh); // Create temporary StructS3DModelVertex structure. StructS3DModelVertex structs3dmodelvertexTemp; // Allocate memory for the vertex structure. memset( &structs3dmodelvertexTemp, 0, sizeof(StructS3DModelVertex) ); // Store the collected vertex data into // our structure to be written to file. structs3dmodelvertexTemp.m_iX = pnt.x; structs3dmodelvertexTemp.m_iY = pnt.z; structs3dmodelvertexTemp.m_iZ = pnt.y; structs3dmodelvertexTemp.m_iNormX = norm.x; structs3dmodelvertexTemp.m_iNormY = norm.z; structs3dmodelvertexTemp.m_iNormZ = norm.y; structs3dmodelvertexTemp.m_iU = uvTexCoordinates.x; structs3dmodelvertexTemp.m_iV = uvTexCoordinates.y; // Write StructS3DModelVertex structure to file. m_fsOutFile.write( (char*)&structs3dmodelvertexTemp.m_iX, sizeof(float) * 8 ); ///////// *ofsTextFile << structs3dmodelvertexTemp.m_iX << " " << structs3dmodelvertexTemp.m_iY << " " << structs3dmodelvertexTemp.m_iZ << " " << structs3dmodelvertexTemp.m_iNormX << " " << structs3dmodelvertexTemp.m_iNormY << " " << structs3dmodelvertexTemp.m_iNormZ << " " << structs3dmodelvertexTemp.m_iU << " " << structs3dmodelvertexTemp.m_iV << " " << "\n"; } ///////////////////////////////////////////////////////////////// // Write Faces ///////////////////////////////////////////////////////////////// ///// *ofsTextFile << "\n" << "[Faces Section]" << "\n"; // get the number of faces. structs3dmeshHeader.m_iFaceCount = mesh.getNumFaces(); // get the offset to the faces. structs3dmeshHeader.m_lFaceOffset = m_fsOutFile.tellg(); // Loop throuh all the faces. for(i = 0; i < structs3dmeshHeader.m_iFaceCount; i++) { // Create a face header. StructS3DFace structs3dfaceHeader; // Allocate memory for the face header. memset(&structs3dfaceHeader, 0, sizeof(StructS3DFace)); // Get face data. structs3dfaceHeader.m_usVertexIndex[0] = mesh.faces.v[0]; structs3dfaceHeader.m_usVertexIndex[1] = mesh.faces[i].v[1]; structs3dfaceHeader.m_usVertexIndex[2] = mesh.faces[i].v[2]; // Write faces to file. m_fsOutFile.write( (char*)&structs3dfaceHeader, sizeof(StructS3DFace) ); ///////// *ofsTextFile << structs3dfaceHeader.m_usVertexIndex[0] << " " << structs3dfaceHeader.m_usVertexIndex[1] << " " << structs3dfaceHeader.m_usVertexIndex[2] << " " << "\n"; // Create temporary StructS3DModelVertex structure. StructS3DModelVertex structs3dmodelvertexTemp; // Allocate memory for the vertex structure. memset( &structs3dmodelvertexTemp, 0, sizeof(StructS3DModelVertex) ); /////////////////////////////////////////////////////////////////////// // Get the vertex coordinates for the first face vertex. Point3 pnt = mesh.getVert(structs3dfaceHeader.m_usVertexIndex[0]) * tm; // Get the vertex normal. Point3 norm = Normalize(mesh.getNormal( structs3dfaceHeader.m_usVertexIndex[0])); // Get the texture coordinates. UVVert& uv = mesh.tVerts[mesh.tvFace[i].t[0]]; // Fill in our vertex structure to be written to file. structs3dmodelvertexTemp.m_iX = pnt.x; structs3dmodelvertexTemp.m_iY = pnt.z; structs3dmodelvertexTemp.m_iZ = pnt.y; structs3dmodelvertexTemp.m_iNormX = norm.x; structs3dmodelvertexTemp.m_iNormY = norm.z; structs3dmodelvertexTemp.m_iNormZ = norm.y; structs3dmodelvertexTemp.m_iU = uv.x; structs3dmodelvertexTemp.m_iV = uv.y; // Write StructS3DModelVertex structure to file. m_fsOutFile.write( (char*)&structs3dmodelvertexTemp.m_iX, sizeof(float) * 8 ); ///////// *ofsTextFile << structs3dmodelvertexTemp.m_iX << " " << structs3dmodelvertexTemp.m_iY << " " << structs3dmodelvertexTemp.m_iZ << " " << structs3dmodelvertexTemp.m_iNormX << " " << structs3dmodelvertexTemp.m_iNormY << " " << structs3dmodelvertexTemp.m_iNormZ << " " << structs3dmodelvertexTemp.m_iU << " " << structs3dmodelvertexTemp.m_iV << " " << "\n"; ////////////////////////////////////////////////////////////////////// // Get the vertex coordinates for the second face vertex. pnt = mesh.getVert(structs3dfaceHeader.m_usVertexIndex[1]) * tm; // Get the vertex normal. norm = Normalize(mesh.getNormal( structs3dfaceHeader.m_usVertexIndex[1])); // Get the texture coordinates. uv = mesh.tVerts[mesh.tvFace[i].t[1]]; // Fill in our vertex structure to be written to file. structs3dmodelvertexTemp.m_iX = pnt.x; structs3dmodelvertexTemp.m_iY = pnt.z; structs3dmodelvertexTemp.m_iZ = pnt.y; structs3dmodelvertexTemp.m_iNormX = norm.x; structs3dmodelvertexTemp.m_iNormY = norm.z; structs3dmodelvertexTemp.m_iNormZ = norm.y; structs3dmodelvertexTemp.m_iU = uv.x; structs3dmodelvertexTemp.m_iV = uv.y; // Write StructS3DModelVertex structure to file. m_fsOutFile.write( (char*)&structs3dmodelvertexTemp.m_iX, sizeof(float) * 8 ); ///////// *ofsTextFile << structs3dmodelvertexTemp.m_iX << " " << structs3dmodelvertexTemp.m_iY << " " << structs3dmodelvertexTemp.m_iZ << " " << structs3dmodelvertexTemp.m_iNormX << " " << structs3dmodelvertexTemp.m_iNormY << " " << structs3dmodelvertexTemp.m_iNormZ << " " << structs3dmodelvertexTemp.m_iU << " " << structs3dmodelvertexTemp.m_iV << " " << "\n"; /////////////////////////////////////////////////////////////////////// // Get the vertex coordinates for the third face vertex. pnt = mesh.getVert(structs3dfaceHeader.m_usVertexIndex[2]) * tm; // Get the vertex normal. norm = Normalize(mesh.getNormal( structs3dfaceHeader.m_usVertexIndex[2])); // Get the texture coordinates. uv = mesh.tVerts[mesh.tvFace[i].t[2]]; // Fill in our vertex structure to be written to file. structs3dmodelvertexTemp.m_iX = pnt.x; structs3dmodelvertexTemp.m_iY = pnt.z; structs3dmodelvertexTemp.m_iZ = pnt.y; structs3dmodelvertexTemp.m_iNormX = norm.x; structs3dmodelvertexTemp.m_iNormY = norm.z; structs3dmodelvertexTemp.m_iNormZ = norm.y; structs3dmodelvertexTemp.m_iU = uv.x; structs3dmodelvertexTemp.m_iV = uv.y; // Write StructS3DModelVertex structure to file. m_fsOutFile.write( (char*)&structs3dmodelvertexTemp.m_iX, sizeof(float) * 8 ); ///////// *ofsTextFile << structs3dmodelvertexTemp.m_iX << " " << structs3dmodelvertexTemp.m_iY << " " << structs3dmodelvertexTemp.m_iZ << " " << structs3dmodelvertexTemp.m_iNormX << " " << structs3dmodelvertexTemp.m_iNormY << " " << structs3dmodelvertexTemp.m_iNormZ << " " << structs3dmodelvertexTemp.m_iU << " " << structs3dmodelvertexTemp.m_iV << " " << "\n"; }// End loop through all faces. ///////////////////////////////////////////////////////////////// // Get texture info. // Get the material for the selected node. Mtl* curMat = ptrINode->GetMtl(); // Create a texture map slot. Texmap* texmapSlot = NULL; // Loop through all the texture maps in the material. for (i=0; i < curMat->NumSubTexmaps(); i++) { // Get the current texture map. texmapSlot = curMat->GetSubTexmap(i); // If the there is a valid texture map. if (texmapSlot) { // If the texture map is a bitmap texture. if ( texmapSlot->ClassID() == Class_ID(BMTEX_CLASS_ID, 0x00) ) { // Get the entire path name of the bitmap texture. TSTR tstrMapName = ((BitmapTex *)texmapSlot)->GetMapName(); // Extract file name. TSTR tstrPathName, tstrFileName; SplitPathFile( tstrMapName, &tstrPathName, &tstrFileName ); // Copy the file name into our structure to be // written to file. _tcscpy( structs3dmeshHeader.m_strTextureName, tstrFileName ); } // End if bitmap texture. } // End if valid texture map slot. } // End loop through all texture maps in the material. ////////////////////////////////////////////////////////////////// // Get the current position in file. long lEndPosition = m_fsOutFile.tellg(); // Go to start position. m_fsOutFile.seekg(lStartPosition); ///// *ofsTextFile << "\n" << "[Mesh Header Section]" << "\n"; // Write mesh header class to file. m_fsOutFile.write( (char*)&structs3dmeshHeader, sizeof(StructS3DMesh) ); ///////// *ofsTextFile << structs3dmeshHeader.m_iS3dmodelvertexCount << endl << structs3dmeshHeader.m_lS3dmodelvertexOffset << endl << structs3dmeshHeader.m_iFaceCount << endl << structs3dmeshHeader.m_lFaceOffset << endl << structs3dmeshHeader.m_strTextureName << endl << "\n"; // Go to end position. m_fsOutFile.seekg(lEndPosition); // Return success. return true; } // Get texture coordinates from a vertex. UVVert getTextureUV(int iVertexIndex, Mesh* mesh) { UVVert uvTextureCoordinates; // If mesh has valid vertices and faces if ( mesh->tVerts && mesh->tvFace ) { // Loop through all the faces. for ( int i = 0; i < mesh->numFaces; i++ ) { // Loop through the 3 vertices of the face. for ( int j = 0; j < 3; j++ ) { // If the vertex index passed in matches // the vertex of the face. if ( mesh->faces[i].v[j] == iVertexIndex ) { // Obtain the texture coordinates for it. uvTextureCoordinates = mesh->tVerts[mesh->tvFace[i].t[j]]; } // End vertex index and face vertex index match } // End face vertex index loop. } // End face loop. // Return the texture coordinates. return uvTextureCoordinates; } // End if valid vertices and faces. // Return failure return NULL; } Here is my importer code: //----------------------------------------------------------------------------- // Name: setModelData() // Desc: Sets the model data by deciphering from the buffer. //----------------------------------------------------------------------------- bool S3DModel::setModelData( S3DSystem* ptrS3dsystemCapsule ) { // Create a local pointer to the memory buffer // containing the 3D model data. const char* ptrCharModelData = m_ptrCharModelData; // Obtain the file version by casting. const unsigned long* ptrUlS3DVersion = ( const unsigned long* ) ptrCharModelData; // If not the correct file version. if ( *ptrUlS3DVersion != s_ulS3DVersion ) { // Notify user. ptrS3dsystemCapsule->displayMessage( "Incorrect S3D model file version. Please only use valid *.s3d files." ); // Return model load failure. return false; } // Skip file version data. ptrCharModelData += sizeof( s_ulS3DVersion ); // Skip model header data. ptrCharModelData += sizeof( StructS3DModel ); // Obtain the mesh structure. m_ptrStructs3dmeshData = ( StructS3DMesh* ) ptrCharModelData; // Save the texture name. strcpy( m_strTextureName, m_ptrStructs3dmeshData->m_strTextureName ); // Skip mesh header data. ptrCharModelData += sizeof( StructS3DMesh ); // Record the current position in the buffer.. const char* ptrCharSavedPosition = ptrCharModelData; // Skip to face data. ptrCharModelData = m_ptrCharModelData + m_ptrStructs3dmeshData->m_lFaceOffset; // Clear the STL vector to store the indices of our faces. m_vecUsIndices.clear(); // Clear the STL vector to store the vertices of our face. m_vecStructs3dmodelvertexContainer.clear(); // Loop through all the face data. for ( int i = 0; i < (m_ptrStructs3dmeshData->m_iFaceCount); i++ ) { // Create a temporary face structure pointer. StructS3DFace* ptrStructs3dfaceTemp; // Obtain the face data by casting. ptrStructs3dfaceTemp = ( StructS3DFace* ) ptrCharModelData; //cout << ptrStructs3dfaceTemp->m_usVertexIndex[0] << " "; //cout << ptrStructs3dfaceTemp->m_usVertexIndex[1] << " "; //cout << ptrStructs3dfaceTemp->m_usVertexIndex[2] << " "; // Store the face data. m_vecUsIndices. push_back( ptrStructs3dfaceTemp->m_usVertexIndex[0] ); m_vecUsIndices. push_back( ptrStructs3dfaceTemp->m_usVertexIndex[1] ); m_vecUsIndices. push_back( ptrStructs3dfaceTemp->m_usVertexIndex[2] ); // Skip this particular face structure. ptrCharModelData += sizeof( StructS3DFace ); // Loop through all the 3 vertices of the face. for ( int j = 0; j < 3; ++j ) { // Create a temporary model vertex structure pointer. StructS3DModelVertex* ptrStructs3dmodelvertexTemp; // Obtain the model vertex data by casting. ptrStructs3dmodelvertexTemp = ( StructS3DModelVertex* ) ptrCharModelData; // Create a temporary model vertex structure. StructS3DModelVertex structs3dmodelvertexTemp; // Fill in the data of the model vertex structure. structs3dmodelvertexTemp.m_iX = ptrStructs3dmodelvertexTemp->m_iX; structs3dmodelvertexTemp.m_iY = ptrStructs3dmodelvertexTemp->m_iY; structs3dmodelvertexTemp.m_iZ = ptrStructs3dmodelvertexTemp->m_iZ; structs3dmodelvertexTemp.m_iNormX = ptrStructs3dmodelvertexTemp->m_iNormX; structs3dmodelvertexTemp.m_iNormY = ptrStructs3dmodelvertexTemp->m_iNormY; structs3dmodelvertexTemp.m_iNormZ = ptrStructs3dmodelvertexTemp->m_iNormZ; structs3dmodelvertexTemp.m_iU = ptrStructs3dmodelvertexTemp->m_iU; structs3dmodelvertexTemp.m_iV = 1 - ptrStructs3dmodelvertexTemp->m_iV; //cout << ptrStructs3dmodelvertexTemp->m_iNormZ << " "; // Store the vertex data. m_vecStructs3dmodelvertexContainer. push_back( structs3dmodelvertexTemp ); // Skip this particular model vertex structure. ptrCharModelData += sizeof( StructS3DModelVertex ); } } // End loop through faces. //cout << m_vecStructs3dmodelvertexContainer[4484].m_iU; //cout << m_vecStructs3dmodelvertexContainer.size() << " "; // Create iterators. std::vector::iterator itrStructs3dmodelvertex = m_vecStructs3dmodelvertexContainer.begin(); // Create vertex buffer. ptrS3dsystemCapsule->createVertexBuffer( sizeof(StructS3DModelVertex) * m_vecStructs3dmodelvertexContainer.size(), sizeof(StructS3DModelVertex), m_ptrStructs3dmeshData->m_iFaceCount, itrStructs3dmodelvertex ); // return success. return true; } //----------------------------------------------------------------------------- // Name: renderModel() // Desc: Renders the loaded model. //----------------------------------------------------------------------------- void S3DModel::renderModel( float fX, float fY, float fZ, S3DSystem* ptrS3dsystemCapsule, S3DRender* ptrS3drenderModule ) { // Ensure position is the one directly infront of camera // by adjusting the view matrix. The size of the fonts // are also scaled. S3DMath::S3DMatrix s3dmatrixView; s3dmatrixView.identity(); s3dmatrixView[0][0] = 0.3f; s3dmatrixView[1][1] = 0.3f; s3dmatrixView[2][2] = 0.3f; s3dmatrixView[3][0] = fX; s3dmatrixView[3][1] = fY; s3dmatrixView[3][2] = fZ; // Invoke setTransforms, which will eventually set our // 3D API''s view matrix. ptrS3drenderModule->setTransforms( ptrS3dsystemCapsule, VIEW_TRANSFORM, &s3dmatrixView ); // Create iterators. std::vector::iterator itrInt = m_vecUsIndices.begin(); std::vector::iterator itrStructs3dmodelvertex = m_vecStructs3dmodelvertexContainer.begin(); // Invoke the render function. ptrS3drenderModule->renderNonIndexed( ptrS3dsystemCapsule, 0, sizeof(StructS3DModelVertex), m_ptrStructs3dmeshData->m_iFaceCount ); /* ptrS3drenderModule->render( ptrS3dsystemCapsule, 0, m_ptrStructs3dmeshData->m_iS3dmodelvertexCount, m_ptrStructs3dmeshData->m_iFaceCount, itrInt, itrStructs3dmodelvertex, sizeof(StructS3DModelVertex) ); */ } Here is my output: www.Sherman3D.com/sherman/error2.jpg Ummm, anybody knows what I am doing wrong? Thanks! ^_^ Best regards, Sherman

Share this post


Link to post
Share on other sites
you are in the incorrect group, because it is a artist group not programmer :-(


-----------------------------------------------

"Cuando se es peon, la unica salida es la revolución"

Share this post


Link to post
Share on other sites
Dear eng3D,

Thanks for your reply. Just trying my luck since my post in the 3D Graphics Programming
forum yielded no replies. ;_;

Best regards,
Sherman
http://www.Sherman3D.com

Share this post


Link to post
Share on other sites