Download

Skeletal Mesh's Render-data to Procedural Mesh

I’ve wrote “CopyProceduralMeshFromSkeletalMeshComponent” method for my practice project,
to implement a gore scene like head-blowing…

But, Some vertices are correctly copied. but, almost vertices couldn’t be copied.

How can i generate procedural mesh correctly?


void UKismetProceduralSkeletalMeshLibrary::CopyProceduralMeshFromSkeletalMeshComponent(USkeletalMeshComponent * SkeletalMeshComponent, int32 LODIndex, UProceduralMeshComponent * ProcMeshComponent, bool bCreateCollision) {
    if (SkeletalMeshComponent && SkeletalMeshComponent->SkeletalMesh && ProcMeshComponent) {
        FSkeletalMeshRenderData* RenderData =  SkeletalMeshComponent->GetSkeletalMeshRenderData();

        if (!RenderData->LODRenderData.IsValidIndex(LODIndex))
            return;
        //SkeletalMeshComponent->MeshObject
        auto& RealRender = RenderData->LODRenderData[LODIndex];
        auto& RenderSections = RealRender.RenderSections;

        auto Indices = RealRender.AdjacencyMultiSizeIndexContainer.GetIndexBuffer();
        auto& Positions = RealRender.StaticVertexBuffers.PositionVertexBuffer;
        auto& OVertices = RealRender.StaticVertexBuffers.StaticMeshVertexBuffer;
        auto& Colors = RealRender.StaticVertexBuffers.ColorVertexBuffer;

        for (int32 i = 0; i < RenderSections.Num(); i++) {
            TMap<int32, int32> MeshToSectionVertMap;
            TArray<FVector> Vertices, Normals;
            TArray<int32> Triangles;
            TArray<FVector2D> UVs, UVs1, UVs2, UVs3;
            TArray<FProcMeshTangent> Tangents;

            auto& ThisSection = RenderSections*;
            uint32 LastIndex = ThisSection.BaseIndex + ThisSection.NumTriangles * 3;

            //ThisSection.DuplicatedVerticesBuffer.DupVertIndexData[0].
            //RealRender.


            for (uint32 J = ThisSection.BaseIndex; J < LastIndex; J++) {
                uint32 MeshVertIndex = Indices->Get(J);

                int32* NewIndexPtr = MeshToSectionVertMap.Find(MeshVertIndex);
                int32 NewIndex = -1;

                if (NewIndexPtr) {
                    NewIndex = *NewIndexPtr;
                    Triangles.Add(NewIndex);
                }

                else {
                    int SectVertIdx = Vertices.Add(
                        Positions.VertexPosition(MeshVertIndex));

                    Normals.Add(OVertices.VertexTangentZ(MeshVertIndex));
                    UVs.Add(OVertices.GetVertexUV(MeshVertIndex, 0));

                    FVector4 TangentX = OVertices.VertexTangentX(MeshVertIndex);
                    FProcMeshTangent NewTangent(TangentX, TangentX.W < 0.f);
                    Tangents.Add(NewTangent);

                    MeshToSectionVertMap.Add(MeshVertIndex, SectVertIdx);
                    Triangles.Add(SectVertIdx);
                }
            }
            /*

            ThisSection.ClothMappingData*/

            TArray<FLinearColor> DummyColors;
            ProcMeshComponent->CreateMeshSection_LinearColor(i,
                Vertices, Triangles, Normals, UVs, UVs1, UVs2, UVs3,
                DummyColors, Tangents, bCreateCollision);
            //RenderSections*.
        }

        ProcMeshComponent->ClearCollisionConvexMeshes();

        if (SkeletalMeshComponent->BodySetup != nullptr)
        {
            // Iterate over all convex hulls on static mesh..
            const int32 NumConvex = SkeletalMeshComponent->BodySetup->AggGeom.ConvexElems.Num();
            for (int ConvexIndex = 0; ConvexIndex < NumConvex; ConvexIndex++)
            {
                // Copy convex verts to ProcMesh
                FKConvexElem& MeshConvex = SkeletalMeshComponent->BodySetup->AggGeom.ConvexElems[ConvexIndex];
                ProcMeshComponent->AddCollisionConvexMesh(MeshConvex.VertexData);
            }
        }

        for (int32 MatIndex = 0; MatIndex < SkeletalMeshComponent->GetNumMaterials(); MatIndex++)
        {
            ProcMeshComponent->SetMaterial(MatIndex, SkeletalMeshComponent->GetMaterial(MatIndex));
        }
    }
}