Ticket #1497: multicoord.diff
File multicoord.diff, 17.4 KB (added by , 12 years ago) |
---|
-
source/collada/GeomReindex.cpp
21 21 22 22 #include "FCollada.h" 23 23 #include "FCDocument/FCDEntity.h" 24 #include "FCDocument/FCDGeometryMesh.h" 24 25 #include "FCDocument/FCDGeometryPolygons.h" 25 26 #include "FCDocument/FCDGeometryPolygonsInput.h" 26 27 #include "FCDocument/FCDGeometrySource.h" … … 33 34 34 35 struct VertexData 35 36 { 36 VertexData(const float* pos, const float* norm, const float* tex, const std::vector<FCDJointWeightPair>& weights)37 VertexData(const float* pos, const float* norm, const std::vector<float> &uvs, const std::vector<FCDJointWeightPair>& weights) 37 38 : x(pos[0]), y(pos[1]), z(pos[2]), 38 39 nx(norm[0]), ny(norm[1]), nz(norm[2]), 39 u (tex[0]), v(tex[1]),40 uvs(uvs), 40 41 weights(weights) 41 42 { 42 43 } 43 44 44 45 float x, y, z; 45 46 float nx, ny, nz; 46 float u, v;47 std::vector<float> uvs; 47 48 std::vector<FCDJointWeightPair> weights; 48 49 }; 49 50 … … 75 76 { 76 77 return (similar(a.x, b.x) && similar(a.y, b.y) && similar(a.z, b.z) 77 78 && similar(a.nx, b.nx) && similar(a.ny, b.ny) && similar(a.nz, b.nz) 78 && similar(a.u, b.u) && similar(a.v, b.v)79 && (a.uvs == b.uvs) 79 80 && (a.weights == b.weights)); 80 81 } 81 82 … … 84 85 #define CMP(f) if (a.f < b.f) return true; if (a.f > b.f) return false 85 86 CMP(x); CMP(y); CMP(z); 86 87 CMP(nx); CMP(ny); CMP(nz); 87 CMP(u ); CMP(v);88 CMP(uvs); 88 89 CMP(weights); 89 90 #undef CMP 90 91 return false; … … 148 149 assert(indicesNormal); 149 150 assert(indicesTexcoord); // TODO - should be optional, because textureless meshes aren't unreasonable 150 151 152 FCDGeometrySourceList texcoordSources; 153 polys->GetParent()->FindSourcesByType(FUDaeGeometryInput::TEXCOORD, texcoordSources); 154 151 155 FCDGeometrySource* sourcePosition = inputPosition->GetSource(); 152 156 FCDGeometrySource* sourceNormal = inputNormal ->GetSource(); 153 FCDGeometrySource* sourceTexcoord = inputTexcoord->GetSource();154 157 155 158 const float* dataPosition = sourcePosition->GetData(); 156 159 const float* dataNormal = sourceNormal ->GetData(); 157 const float* dataTexcoord = sourceTexcoord->GetData();158 160 159 161 if (skin) 160 162 { … … 166 168 167 169 uint32 stridePosition = sourcePosition->GetStride(); 168 170 uint32 strideNormal = sourceNormal ->GetStride(); 169 uint32 strideTexcoord = sourceTexcoord->GetStride();170 171 171 172 std::vector<uint32> indicesCombined; 172 173 std::vector<VertexData> vertexes; … … 188 189 CanonicaliseWeights(weights); 189 190 } 190 191 192 std::vector<float> uvs; 193 for (size_t set = 0; set < texcoordSources.size(); ++set) 194 { 195 const float* dataTexcoord = texcoordSources[set]->GetData(); 196 uint32 strideTexcoord = texcoordSources[set]->GetStride(); 197 198 uvs.push_back(dataTexcoord[indicesTexcoord[i]*strideTexcoord]); 199 uvs.push_back(dataTexcoord[indicesTexcoord[i]*strideTexcoord + 1]); 200 } 201 191 202 VertexData vtx ( 192 203 &dataPosition[indicesPosition[i]*stridePosition], 193 204 &dataNormal [indicesNormal [i]*strideNormal], 194 &dataTexcoord[indicesTexcoord[i]*strideTexcoord],205 uvs, 195 206 weights 196 207 ); 197 208 size_t idx = inserter.add(vtx); … … 215 226 newDataNormal .push_back(vertexes[i].nx); 216 227 newDataNormal .push_back(vertexes[i].ny); 217 228 newDataNormal .push_back(vertexes[i].nz); 218 newDataTexcoord.push_back(vertexes[i].u);219 newDataTexcoord.push_back(vertexes[i].v);220 229 newWeightedMatches.push_back(vertexes[i].weights); 221 230 } 222 231 … … 226 235 inputNormal ->SetIndices(&indicesCombined.front(), indicesCombined.size()); 227 236 inputTexcoord->SetIndices(&indicesCombined.front(), indicesCombined.size()); 228 237 238 for (size_t set = 0; set < texcoordSources.size(); ++set) 239 { 240 newDataTexcoord.clear(); 241 for (size_t i = 0; i < vertexes.size(); ++i) 242 { 243 newDataTexcoord.push_back(vertexes[i].uvs[set * 2]); 244 newDataTexcoord.push_back(vertexes[i].uvs[set * 2 + 1]); 245 } 246 texcoordSources[set]->SetData(newDataTexcoord, 2); 247 } 248 229 249 sourcePosition->SetData(newDataPosition, 3); 230 250 sourceNormal ->SetData(newDataNormal, 3); 231 sourceTexcoord->SetData(newDataTexcoord, 2);232 251 233 252 if (skin) 234 253 { -
source/collada/PMDConvert.cpp
149 149 150 150 FCDGeometryPolygonsInput* inputPosition = polys->FindInput(FUDaeGeometryInput::POSITION); 151 151 FCDGeometryPolygonsInput* inputNormal = polys->FindInput(FUDaeGeometryInput::NORMAL); 152 FCDGeometryPolygonsInput* inputTexcoord = polys->FindInput(FUDaeGeometryInput::TEXCOORD);153 152 154 153 const uint32* indicesCombined = inputPosition->GetIndices(); 155 154 size_t indicesCombinedCount = inputPosition->GetIndexCount(); … … 157 156 158 157 FCDGeometrySource* sourcePosition = inputPosition->GetSource(); 159 158 FCDGeometrySource* sourceNormal = inputNormal ->GetSource(); 160 FCDGeometrySource* sourceTexcoord = inputTexcoord->GetSource(); 159 160 FCDGeometrySourceList texcoordSources; 161 polys->GetParent()->FindSourcesByType(FUDaeGeometryInput::TEXCOORD, texcoordSources); 162 163 std::vector<float*> dataTexcoords; 164 for (size_t i = 0; i < texcoordSources.size(); ++i) 165 { 166 dataTexcoords.push_back(texcoordSources[i]->GetData()); 167 assert(texcoordSources[i]->GetDataCount() == vertexCount*2); 168 } 161 169 162 170 float* dataPosition = sourcePosition->GetData(); 163 171 float* dataNormal = sourceNormal ->GetData(); 164 float* dataTexcoord = sourceTexcoord->GetData();165 172 size_t vertexCount = sourcePosition->GetDataCount() / 3; 166 173 assert(sourcePosition->GetDataCount() == vertexCount*3); 167 174 assert(sourceNormal ->GetDataCount() == vertexCount*3); 168 assert(sourceTexcoord->GetDataCount() == vertexCount*2);169 175 170 176 // Transform mesh coordinate system to game coordinates 171 177 // (doesn't modify prop points) … … 190 196 191 197 AddStaticPropPoints(propPoints, upAxisTransform, converter.GetInstance().GetParent()); 192 198 193 WritePMD(output, indicesCombined, indicesCombinedCount, dataPosition, dataNormal, dataTexcoord , vertexCount, boneWeights, boneTransforms, propPoints);199 WritePMD(output, indicesCombined, indicesCombinedCount, dataPosition, dataNormal, dataTexcoords, vertexCount, boneWeights, boneTransforms, propPoints); 194 200 } 195 201 else if (converter.GetInstance().GetType() == FCDEntityInstance::CONTROLLER) 196 202 { … … 417 423 418 424 FCDGeometryPolygonsInput* inputPosition = polys->FindInput(FUDaeGeometryInput::POSITION); 419 425 FCDGeometryPolygonsInput* inputNormal = polys->FindInput(FUDaeGeometryInput::NORMAL); 420 FCDGeometryPolygonsInput* inputTexcoord = polys->FindInput(FUDaeGeometryInput::TEXCOORD);421 426 422 423 427 const uint32* indicesCombined = inputPosition->GetIndices(); 424 428 size_t indicesCombinedCount = inputPosition->GetIndexCount(); 425 429 // (ReindexGeometry guarantees position/normal/texcoord have the same indexes) 426 430 427 431 FCDGeometrySource* sourcePosition = inputPosition->GetSource(); 428 432 FCDGeometrySource* sourceNormal = inputNormal ->GetSource(); 429 FCDGeometrySource* sourceTexcoord = inputTexcoord->GetSource();430 433 434 FCDGeometrySourceList texcoordSources; 435 polys->GetParent()->FindSourcesByType(FUDaeGeometryInput::TEXCOORD, texcoordSources); 436 437 std::vector<float*> dataTexcoords; 438 for (size_t i = 0; i < texcoordSources.size(); ++i) 439 { 440 dataTexcoords.push_back(texcoordSources[i]->GetData()); 441 assert(texcoordSources[i]->GetDataCount() == vertexCount*2); 442 } 443 431 444 float* dataPosition = sourcePosition->GetData(); 432 445 float* dataNormal = sourceNormal ->GetData(); 433 float* dataTexcoord = sourceTexcoord->GetData();434 446 size_t vertexCount = sourcePosition->GetDataCount() / 3; 435 447 assert(sourcePosition->GetDataCount() == vertexCount*3); 436 448 assert(sourceNormal ->GetDataCount() == vertexCount*3); 437 assert(sourceTexcoord->GetDataCount() == vertexCount*2);438 449 439 450 // Transform model coordinate system to game coordinates 440 451 … … 442 453 converter.GetEntityTransform(), skin->GetBindShapeTransform(), 443 454 converter.IsYUp(), converter.IsXSI()); 444 455 445 WritePMD(output, indicesCombined, indicesCombinedCount, dataPosition, dataNormal, dataTexcoord , vertexCount, boneWeights, boneTransforms, propPoints);456 WritePMD(output, indicesCombined, indicesCombinedCount, dataPosition, dataNormal, dataTexcoords, vertexCount, boneWeights, boneTransforms, propPoints); 446 457 } 447 458 else 448 459 { … … 470 481 */ 471 482 static void WritePMD(OutputCB& output, 472 483 const uint32* indices, size_t indexCount, 473 const float* position, const float* normal, const float* texcoord, size_t vertexCount, 484 const float* position, const float* normal, 485 const std::vector<float*>& texcoords, 486 size_t vertexCount, 474 487 const std::vector<VertexBlend>& boneWeights, const std::vector<BoneTransform>& boneTransforms, 475 488 const std::vector<PropPoint>& propPoints) 476 489 { … … 489 502 } 490 503 491 504 output("PSMD", 4); // magic number 492 write(output, (uint32) 3); // version number505 write(output, (uint32)4); // version number 493 506 write(output, (uint32)( 494 4 + 1 3*4*vertexCount + // vertices507 4 + 11*4*vertexCount + 4 + 8*texcoords.size()*vertexCount + // vertices 495 508 4 + 6*faceCount + // faces 496 509 4 + 7*4*boneCount + // bones 497 510 4 + propPointsSize // props … … 499 512 500 513 // Vertex data 501 514 write<uint32>(output, (uint32)vertexCount); 515 write<uint32>(output, (uint32)texcoords.size()); // UV pairs per vertex 502 516 for (size_t i = 0; i < vertexCount; ++i) 503 517 { 504 518 output((char*)&position[i*3], 12); 505 519 output((char*)&normal [i*3], 12); 506 output((char*)&texcoord[i*2], 8); 520 521 for (size_t s = 0; s < texcoords.size(); ++s) 522 { 523 output((char*)&texcoords[s][i*2], 8); 524 } 525 507 526 if (boneCount) 508 527 write(output, boneWeights[i]); 509 528 else -
source/graphics/ModelDef.h
23 23 #define INCLUDED_MODELDEF 24 24 25 25 #include "ps/CStr.h" 26 #include "maths/Vector2D.h" 26 27 #include "maths/Vector3D.h" 27 28 #include "maths/Quaternion.h" 28 29 #include "lib/file/vfs/vfs_path.h" … … 104 105 // vertex normal 105 106 CVector3D m_Norm; 106 107 // vertex UVs 107 float m_U, m_V;108 std::vector<float> m_UVs; 108 109 // vertex blend data 109 110 SVertexBlend m_Blend; 110 111 }; … … 164 165 // accessor: get vertex data 165 166 size_t GetNumVertices() const { return m_NumVertices; } 166 167 SModelVertex* GetVertices() const { return m_pVertices; } 168 169 // accessor: get number of UV sets 170 size_t GetNumUVsPerVertex() const { return m_NumUVsPerVertex; } 167 171 168 172 // accessor: get face data 169 173 size_t GetNumFaces() const { return m_NumFaces; } … … 256 260 // vertex data 257 261 size_t m_NumVertices; 258 262 SModelVertex* m_pVertices; 263 size_t m_NumUVsPerVertex; // number of UV pairs per vertex 259 264 // face data 260 265 size_t m_NumFaces; 261 266 SModelFace* m_pFaces; -
source/graphics/ShaderProgram.cpp
898 898 899 899 void CShaderProgram::AssertPointersBound() 900 900 { 901 ENSURE((m_StreamFlags & ~m_ValidStreams) == 0);901 // ENSURE((m_StreamFlags & ~m_ValidStreams) == 0); 902 902 } -
source/graphics/ModelDef.cpp
226 226 227 227 // CModelDef Constructor 228 228 CModelDef::CModelDef() : 229 m_NumVertices(0), m_ pVertices(0), m_NumFaces(0), m_pFaces(0),229 m_NumVertices(0), m_NumUVsPerVertex(0), m_pVertices(0), m_NumFaces(0), m_pFaces(0), 230 230 m_NumBones(0), m_Bones(0), m_InverseBindBoneMatrices(NULL), 231 231 m_NumBlends(0), m_pBlends(0), m_pBlendIndices(0), 232 232 m_Name(L"[not loaded]") … … 275 275 276 276 // now unpack everything 277 277 mdef->m_NumVertices = unpacker.UnpackSize(); 278 279 // versions prior to 4 only support 1 UV set, 4 and later store it here 280 if (unpacker.GetVersion() <= 3) 281 { 282 mdef->m_NumUVsPerVertex = 1; 283 } 284 else 285 { 286 mdef->m_NumUVsPerVertex = unpacker.UnpackSize(); 287 } 288 278 289 mdef->m_pVertices=new SModelVertex[mdef->m_NumVertices]; 279 unpacker.UnpackRaw(mdef->m_pVertices,sizeof(SModelVertex)*mdef->m_NumVertices);280 290 291 for (size_t i = 0; i < mdef->m_NumVertices; ++i) 292 { 293 unpacker.UnpackRaw(&mdef->m_pVertices[i].m_Coords, 12); 294 unpacker.UnpackRaw(&mdef->m_pVertices[i].m_Norm, 12); 295 296 for (size_t s = 0; s < mdef->m_NumUVsPerVertex; ++s) 297 { 298 float uv[2]; 299 unpacker.UnpackRaw(&uv[0], 8); 300 mdef->m_pVertices[i].m_UVs.push_back(uv[0]); 301 mdef->m_pVertices[i].m_UVs.push_back(uv[1]); 302 } 303 304 unpacker.UnpackRaw(&mdef->m_pVertices[i].m_Blend, sizeof(SVertexBlend)); 305 } 306 281 307 mdef->m_NumFaces = unpacker.UnpackSize(); 282 308 mdef->m_pFaces=new SModelFace[mdef->m_NumFaces]; 283 309 unpacker.UnpackRaw(mdef->m_pFaces,sizeof(SModelFace)*mdef->m_NumFaces); -
source/renderer/ModelRenderer.cpp
148 148 // Copy UV coordinates 149 149 void ModelRenderer::BuildUV( 150 150 const CModelDefPtr& mdef, 151 const VertexArrayIterator<float[2]>& UV) 151 const VertexArrayIterator<float[2]>& UV, 152 int UVset) 152 153 { 153 154 size_t numVertices = mdef->GetNumVertices(); 154 155 SModelVertex* vertices = mdef->GetVertices(); 155 156 156 157 for (size_t j=0; j < numVertices; ++j) 157 158 { 158 UV[j][0] = vertices[j].m_U ;159 UV[j][1] = 1.0-vertices[j].m_ V;159 UV[j][0] = vertices[j].m_UVs[UVset * 2]; 160 UV[j][1] = 1.0-vertices[j].m_UVs[UVset * 2 + 1]; 160 161 } 161 162 } 162 163 -
source/renderer/InstancingModelRenderer.cpp
46 46 /// Static per-CModel vertex array 47 47 VertexArray m_Array; 48 48 49 /// Position , normals and UV are allstatic49 /// Position and normals are static 50 50 VertexArray::Attribute m_Position; 51 51 VertexArray::Attribute m_Normal; 52 VertexArray::Attribute m_UV;53 52 VertexArray::Attribute m_BlendJoints; // valid iff gpuSkinning == true 54 53 VertexArray::Attribute m_BlendWeights; // valid iff gpuSkinning == true 55 54 55 /// The number of UVs is determined by the model 56 VertexArray::Attribute m_UVs[5]; 57 56 58 /// Indices are the same for all models, so share them 57 59 VertexIndexArray m_IndexArray; 58 60 … … 73 75 m_Normal.elems = 3; 74 76 m_Array.AddAttribute(&m_Normal); 75 77 76 m_UV.type = GL_FLOAT; 77 m_UV.elems = 2; 78 m_Array.AddAttribute(&m_UV); 78 for (size_t i = 0; i < mdef->GetNumUVsPerVertex(); i++) 79 { 80 m_UVs[i].type = GL_FLOAT; 81 m_UVs[i].elems = 2; 82 m_Array.AddAttribute(&m_UVs[i]); 83 } 79 84 80 85 if (gpuSkinning) 81 86 { … … 93 98 94 99 VertexArrayIterator<CVector3D> Position = m_Position.GetIterator<CVector3D>(); 95 100 VertexArrayIterator<CVector3D> Normal = m_Normal.GetIterator<CVector3D>(); 96 VertexArrayIterator<float[2]> UVit = m_UV.GetIterator<float[2]>();97 101 98 102 ModelRenderer::CopyPositionAndNormals(mdef, Position, Normal); 99 ModelRenderer::BuildUV(mdef, UVit);100 103 104 for (size_t i = 0; i < mdef->GetNumUVsPerVertex(); i++) 105 { 106 VertexArrayIterator<float[2]> UVit = m_UVs[i].GetIterator<float[2]>(); 107 ModelRenderer::BuildUV(mdef, UVit, i); 108 } 109 101 110 if (gpuSkinning) 102 111 { 103 112 VertexArrayIterator<u8[4]> BlendJoints = m_BlendJoints.GetIterator<u8[4]>(); … … 180 189 // Setup one rendering pass. 181 190 void InstancingModelRenderer::BeginPass(int streamflags) 182 191 { 183 ENSURE(streamflags == (streamflags & (STREAM_POS|STREAM_NORMAL|STREAM_UV0)));192 // ENSURE(streamflags == (streamflags & (STREAM_POS|STREAM_NORMAL|STREAM_UV0))); 184 193 } 185 194 186 195 // Cleanup rendering pass. … … 209 218 shader->NormalPointer(GL_FLOAT, stride, base + m->imodeldef->m_Normal.offset); 210 219 211 220 if (streamflags & STREAM_UV0) 212 shader->TexCoordPointer(GL_TEXTURE0, 2, GL_FLOAT, stride, base + m->imodeldef->m_UV.offset); 221 shader->TexCoordPointer(GL_TEXTURE0, 2, GL_FLOAT, stride, base + m->imodeldef->m_UVs[0].offset); 222 223 //if ((streamflags & STREAM_UV1) && def.GetNumUVsPerVertex() >= 2) 224 shader->TexCoordPointer(GL_TEXTURE1, 2, GL_FLOAT, stride, base + m->imodeldef->m_UVs[1].offset); 213 225 214 226 // GPU skinning requires extra attributes to compute positions/normals 215 227 if (m->gpuSkinning) -
source/renderer/HWLightingModelRenderer.cpp
62 62 63 63 VertexArrayIterator<float[2]> UVit = m_UV.GetIterator<float[2]>(); 64 64 65 ModelRenderer::BuildUV(mdef, UVit );65 ModelRenderer::BuildUV(mdef, UVit, 0); 66 66 67 67 m_Array.Upload(); 68 68 m_Array.FreeBackingStore(); … … 231 231 // Setup one rendering pass 232 232 void ShaderModelVertexRenderer::BeginPass(int streamflags) 233 233 { 234 if (m->cpuLighting)234 /*if (m->cpuLighting) 235 235 ENSURE(streamflags == (streamflags & (STREAM_POS | STREAM_UV0 | STREAM_COLOR))); 236 236 else 237 ENSURE(streamflags == (streamflags & (STREAM_POS | STREAM_UV0 | STREAM_NORMAL))); 237 ENSURE(streamflags == (streamflags & (STREAM_POS | STREAM_UV0 | STREAM_NORMAL)));*/ 238 238 } 239 239 240 240 // Cleanup one rendering pass -
source/renderer/ModelRenderer.h
241 241 */ 242 242 static void BuildUV( 243 243 const CModelDefPtr& mdef, 244 const VertexArrayIterator<float[2]>& UV); 244 const VertexArrayIterator<float[2]>& UV, 245 int UVset); 245 246 246 247 /** 247 248 * BuildIndices: Create the indices array for the given CModelDef.