diff --git a/common/lc_array.h b/common/lc_array.h index ee39051a..6f96ba35 100644 --- a/common/lc_array.h +++ b/common/lc_array.h @@ -85,7 +85,7 @@ public: void SetSize(int NewSize) { if (NewSize > mAlloc) - AllocGrow(NewSize - mAlloc); + AllocGrow(NewSize - mLength); mLength = NewSize; } diff --git a/common/lc_library.cpp b/common/lc_library.cpp index b185dd72..59109eb1 100644 --- a/common/lc_library.cpp +++ b/common/lc_library.cpp @@ -1765,27 +1765,51 @@ void lcLibraryMeshData::TestQuad(int* QuadIndices, const lcVector3* Vertices) } } -void lcLibraryMeshData::AddLine(lcMeshDataType MeshDataType, int LineType, lcuint32 ColorCode, const lcVector3* Vertices) +lcLibraryMeshSection* lcLibraryMeshData::AddSection(lcMeshDataType MeshDataType, LC_MESH_PRIMITIVE_TYPE PrimitiveType, lcuint32 ColorCode, lcTexture* Texture) { - lcLibraryMeshSection* Section = NULL; - int SectionIdx; - LC_MESH_PRIMITIVE_TYPE PrimitiveType = (LineType == 2) ? LC_MESH_LINES : LC_MESH_TRIANGLES; lcArray& Sections = mSections[MeshDataType]; + lcLibraryMeshSection* Section; - for (SectionIdx = 0; SectionIdx < Sections.GetSize(); SectionIdx++) + for (int SectionIdx = 0; SectionIdx < Sections.GetSize(); SectionIdx++) { Section = Sections[SectionIdx]; - if (Section->mColor == ColorCode && Section->mPrimitiveType == PrimitiveType && Section->mTexture == NULL) - break; + if (Section->mColor == ColorCode && Section->mPrimitiveType == PrimitiveType && Section->mTexture == Texture) + return Section; } - if (SectionIdx == Sections.GetSize()) - { - Section = new lcLibraryMeshSection(PrimitiveType, ColorCode, NULL); + Section = new lcLibraryMeshSection(PrimitiveType, ColorCode, Texture); + Sections.Add(Section); - Sections.Add(Section); - } + return Section; +} + +void lcLibraryMeshData::AddVertices(lcMeshDataType MeshDataType, int VertexCount, int* BaseVertex, lcVertex** VertexBuffer) +{ + lcArray& Vertices = mVertices[MeshDataType]; + int CurrentSize = Vertices.GetSize(); + + Vertices.SetSize(CurrentSize + VertexCount); + + *BaseVertex = CurrentSize; + *VertexBuffer = &Vertices[CurrentSize]; +} + +void lcLibraryMeshData::AddIndices(lcMeshDataType MeshDataType, LC_MESH_PRIMITIVE_TYPE PrimitiveType, lcuint32 ColorCode, int IndexCount, lcuint32** IndexBuffer) +{ + lcLibraryMeshSection* Section = AddSection(MeshDataType, PrimitiveType, ColorCode, NULL); + lcArray& Indices = Section->mIndices; + int CurrentSize = Indices.GetSize(); + + Indices.SetSize(CurrentSize + IndexCount); + + *IndexBuffer = &Indices[CurrentSize]; +} + +void lcLibraryMeshData::AddLine(lcMeshDataType MeshDataType, int LineType, lcuint32 ColorCode, const lcVector3* Vertices) +{ + LC_MESH_PRIMITIVE_TYPE PrimitiveType = (LineType == 2) ? LC_MESH_LINES : LC_MESH_TRIANGLES; + lcLibraryMeshSection* Section = AddSection(MeshDataType, PrimitiveType, ColorCode, NULL); int QuadIndices[4] = { 0, 1, 2, 3 }; @@ -1848,25 +1872,8 @@ void lcLibraryMeshData::AddLine(lcMeshDataType MeshDataType, int LineType, lcuin void lcLibraryMeshData::AddTexturedLine(lcMeshDataType MeshDataType, int LineType, lcuint32 ColorCode, const lcLibraryTextureMap& Map, const lcVector3* Vertices) { - lcLibraryMeshSection* Section = NULL; - int SectionIdx; LC_MESH_PRIMITIVE_TYPE PrimitiveType = (LineType == 2) ? LC_MESH_TEXTURED_LINES : LC_MESH_TEXTURED_TRIANGLES; - lcArray& Sections = mSections[MeshDataType]; - - for (SectionIdx = 0; SectionIdx < Sections.GetSize(); SectionIdx++) - { - Section = Sections[SectionIdx]; - - if (Section->mColor == ColorCode && Section->mPrimitiveType == PrimitiveType && Section->mTexture == Map.Texture) - break; - } - - if (SectionIdx == Sections.GetSize()) - { - Section = new lcLibraryMeshSection(PrimitiveType, ColorCode, Map.Texture); - - Sections.Add(Section); - } + lcLibraryMeshSection* Section = AddSection(MeshDataType, PrimitiveType, ColorCode, Map.Texture); int QuadIndices[4] = { 0, 1, 2, 3 }; diff --git a/common/lc_library.h b/common/lc_library.h index a1aefa98..f8f860fc 100644 --- a/common/lc_library.h +++ b/common/lc_library.h @@ -78,6 +78,9 @@ public: mSections[MeshDataIdx].DeleteAll(); } + lcLibraryMeshSection* AddSection(lcMeshDataType MeshDataType, LC_MESH_PRIMITIVE_TYPE PrimitiveType, lcuint32 ColorCode, lcTexture* Texture); + void AddVertices(lcMeshDataType MeshDataType, int VertexCount, int* BaseVertex, lcVertex** VertexBuffer); + void AddIndices(lcMeshDataType MeshDataType, LC_MESH_PRIMITIVE_TYPE PrimitiveType, lcuint32 ColorCode, int IndexCount, lcuint32** IndexBuffer); void AddLine(lcMeshDataType MeshDataType, int LineType, lcuint32 ColorCode, const lcVector3* Vertices); void AddTexturedLine(lcMeshDataType MeshDataType, int LineType, lcuint32 ColorCode, const lcLibraryTextureMap& Map, const lcVector3* Vertices); void AddMeshData(const lcLibraryMeshData& Data, const lcMatrix44& Transform, lcuint32 CurrentColorCode, lcLibraryTextureMap* TextureMap, lcMeshDataType OverrideDestIndex); diff --git a/common/lc_synth.cpp b/common/lc_synth.cpp index 4132bb43..342f863a 100644 --- a/common/lc_synth.cpp +++ b/common/lc_synth.cpp @@ -365,14 +365,21 @@ void lcSynthInfo::AddFlexibleAxleParts(lcMemFile& File, const lcArray& Sections) const +void lcSynthInfo::AddStringBraidedParts(lcMemFile& File, lcLibraryMeshData& MeshData, const lcArray& Sections) const { + for (int SectionIdx = 0; SectionIdx < Sections.GetSize(); SectionIdx++) + { + lcMatrix33 Transform = lcMul(lcMatrix33(lcVector3(0.0f, 1.0f, 0.0f), lcVector3(1.0f, 0.0f, 0.0f), lcVector3(0.0f, 0.0f, 1.0f)), lcMatrix33(Sections[SectionIdx])); + lcVector3 Offset = Sections[SectionIdx].GetTranslation(); + Sections[SectionIdx] = lcMatrix44(Transform, Offset); + } + char Line[256]; { const int SectionIdx = 0; - lcMatrix33 Transform(lcMul(lcMatrix33(lcVector3(0.0f, 1.0f, 0.0f), lcVector3(1.0f, 0.0f, 0.0f), lcVector3(0.0f, 0.0f, 1.0f)), lcMatrix33(Sections[SectionIdx]))); - lcVector3 Offset = lcMul31(lcVector3(0.0f, -8.0f, 0.0f), Sections[SectionIdx]); + lcMatrix33 Transform(Sections[SectionIdx]); + lcVector3 Offset = lcMul31(lcVector3(-8.0f, 0.0f, 0.0f), Sections[SectionIdx]); sprintf(Line, "1 16 %f %f %f %f %f %f %f %f %f %f %f %f 572A.DAT\n", Offset[0], Offset[1], Offset[2], Transform[0][0], Transform[1][0], Transform[2][0], Transform[0][1], Transform[1][1], Transform[2][1], Transform[0][2], Transform[1][2], Transform[2][2]); @@ -381,56 +388,101 @@ void lcSynthInfo::AddStringBraidedParts(lcMemFile& File, const lcArrayPosition = Vertex; + VertexBuffer++; + + if (SegmentIdx != NumSegments) + { + *IndexBuffer++ = BaseVertex; + *IndexBuffer++ = BaseVertex + 1; + BaseVertex++; + } } } - lcMatrix33 Transform = lcMul(lcMatrix33(lcVector3(1.5f, 0.0f, 0.0f), lcVector3(0.0f, 4.0f, 0.0f), lcVector3(0.0f, 0.0f, 1.5f)), lcMatrix33(Sections[SectionIdx])); - lcVector3 Offset = lcMul31(lcVector3(1.5f, 0.0f, 0.0f), Sections[SectionIdx]); + BaseVertex++; + } - sprintf(Line, "1 16 %f %f %f %f %f %f %f %f %f %f %f %f 4-4CYLI.DAT\n", Offset[0], Offset[1], Offset[2], Transform[0][0], Transform[1][0], Transform[2][0], - Transform[0][1], Transform[1][1], Transform[2][1], Transform[0][2], Transform[1][2], Transform[2][2]); - File.WriteBuffer(Line, strlen(Line)); + int NumSlices = 16; + MeshData.AddVertices(LC_MESHDATA_SHARED, NumSlices * ((Sections.GetSize() - 2) * NumSegments + 1), &BaseVertex, &VertexBuffer); + MeshData.AddIndices(LC_MESHDATA_SHARED, LC_MESH_TRIANGLES, 16, NumSlices * (Sections.GetSize() - 2) * NumSegments * 6, &IndexBuffer); + + for (int SectionIdx = 1; SectionIdx < Sections.GetSize() - 1; SectionIdx++) + { + lcMatrix33 Transform1 = lcMatrix33(Sections[SectionIdx]); + lcMatrix33 Transform2 = lcMatrix33(Sections[SectionIdx + 1]); + lcVector3 Offset1 = Sections[SectionIdx].GetTranslation(); + lcVector3 Offset2 = Sections[SectionIdx + 1].GetTranslation(); + + for (int SegmentIdx = 0; SegmentIdx < ((SectionIdx < Sections.GetSize() - 2) ? NumSegments : NumSegments + 1); SegmentIdx++) + { + float t1 = (float)SegmentIdx / (float)NumSegments; + int BaseX = 8; + int BaseY = 4; + + for (int SliceIdx = 0; SliceIdx < NumSlices; SliceIdx++) + { + lcVector3 Vertex11 = lcVector3(t1 * 4.0f, PositionTable[(BaseX + SliceIdx) % NumSlices], PositionTable[(BaseY + SliceIdx) % NumSlices]) + lcVector3(0.0f, 1.5f, 0.0f); + lcVector3 Vertex12 = lcVector3((1.0f - t1) * -4.0f, PositionTable[(BaseX + SliceIdx) % NumSlices], PositionTable[(BaseY + SliceIdx) % NumSlices]) + lcVector3(0.0f, 1.5f, 0.0f); + + lcVector3 Vertex1 = (lcMul(Vertex11, Transform1) + Offset1) * (1.0f - t1) + (lcMul(Vertex12, Transform2) + Offset2) * t1; + + VertexBuffer->Position = Vertex1; + VertexBuffer++; + + if (SegmentIdx != NumSegments) + { + *IndexBuffer++ = BaseVertex + SliceIdx; + *IndexBuffer++ = BaseVertex + (SliceIdx + 1) % NumSlices; + *IndexBuffer++ = BaseVertex + (SliceIdx + 1) % NumSlices + NumSlices; + + *IndexBuffer++ = BaseVertex + SliceIdx + NumSlices; + *IndexBuffer++ = BaseVertex + SliceIdx; + *IndexBuffer++ = BaseVertex + (SliceIdx + 1) % NumSlices + NumSlices; + } + } + + BaseVertex += NumSlices; + } } { const int SectionIdx = Sections.GetSize() - 1; - lcMatrix33 Transform(lcMul(lcMatrix33(lcVector3(0.0f, 1.0f, 0.0f), lcVector3(1.0f, 0.0f, 0.0f), lcVector3(0.0f, 0.0f, 1.0f)), lcMatrix33(Sections[SectionIdx]))); - lcVector3 Offset = lcMul31(lcVector3(0.0f, 8.0f, 0.0f), Sections[SectionIdx]); + lcMatrix33 Transform(Sections[SectionIdx]); + lcVector3 Offset = lcMul31(lcVector3(8.0f, 0.0f, 0.0f), Sections[SectionIdx]); sprintf(Line, "1 16 %f %f %f %f %f %f %f %f %f %f %f %f 572A.DAT\n", Offset[0], Offset[1], Offset[2], Transform[0][0], Transform[1][0], Transform[2][0], Transform[0][1], Transform[1][1], Transform[2][1], Transform[0][2], Transform[1][2], Transform[2][2]); @@ -444,6 +496,7 @@ lcMesh* lcSynthInfo::CreateMesh(const lcArray& ControlPoint lcArray Sections; CalculateSections(ControlPoints, Sections, NULL, NULL); + lcLibraryMeshData MeshData; lcMemFile File; // todo: rewrite this to pass the parts directly switch (mType) @@ -457,13 +510,12 @@ lcMesh* lcSynthInfo::CreateMesh(const lcArray& ControlPoint break; case LC_SYNTH_PIECE_STRING_BRAIDED: - AddStringBraidedParts(File, Sections); + AddStringBraidedParts(File, MeshData, Sections); break; } File.WriteU8(0); - lcLibraryMeshData MeshData; lcArray TextureStack; File.Seek(0, SEEK_SET); diff --git a/common/lc_synth.h b/common/lc_synth.h index f8227527..549b7614 100644 --- a/common/lc_synth.h +++ b/common/lc_synth.h @@ -17,6 +17,8 @@ struct lcSynthComponent float Length; }; +class lcLibraryMeshData; + class lcSynthInfo { public: @@ -30,7 +32,7 @@ protected: void CalculateSections(const lcArray& ControlPoints, lcArray& Sections, void(*SectionCallback)(const lcVector3& CurvePoint, int SegmentIndex, float t, void* Param), void* CallbackParam) const; void AddRibbedHoseParts(lcMemFile& File, const lcArray& Sections) const; void AddFlexibleAxleParts(lcMemFile& File, const lcArray& Sections) const; - void AddStringBraidedParts(lcMemFile& File, const lcArray& Sections) const; + void AddStringBraidedParts(lcMemFile& File, lcLibraryMeshData& MeshData, const lcArray& Sections) const; lcSynthType mType; lcSynthComponent mStart;