Stitching together meshes, issues with Cloth.

Hi,

In our game, we have different uniforms per character and we can add any type of shoes to the character. To make sure that they are synchronized visually, we merge the 2 skins (shoes and body) together at runtime using USkeletalMergingLibrary. The cloth simulation works great without the merge but if I tried to merge the shoes with the rest of the body, then the cloth simulation stops working (it looks like before without cloth). I have added the same cloth asset in the shoes but it didn’t make a difference. Is it possible to merge 2 skeletal meshes with cloth? If yes, then what am I doing wrong (see the code below)? Thanks.

Laurent

`void CopyClothFromMesh(USkeletalMesh* sourceMesh, USkeletalMesh* targetMesh)
{
if (!IsValid(sourceMesh) || !IsValid(targetMesh))
return;

// Iterate over clothing assets in the source mesh.
for (UClothingAssetBase* clothingAsset : sourceMesh->GetMeshClothingAssets())
{
if (!IsValid(clothingAsset))
continue;

// Duplicate the clothing asset.
UClothingAssetBase* duplicatedAsset = DuplicateObject(clothingAsset, targetMesh);

if (IsValid(duplicatedAsset))
{
// Add to target mesh
targetMesh->AddClothingAsset(duplicatedAsset);
}
}
}

// Do the merge of shoes and body.
FSkeletalMeshMergeParams mergeParams;

mergeParams.MeshesToMerge.Add(characterMesh);
mergeParams.MeshesToMerge.Add(MotionGroupAsset->Shoes);

mergeParams.Skeleton = characterMesh->GetSkeleton();
mergeParams.StripTopLODS = 0;
mergeParams.bNeedsCpuAccess = true;
mergeParams.bSkeletonBefore = true;

USkeletalMesh* mergedMesh = USkeletalMergingLibrary::MergeMeshes(mergeParams);

UPhysicsAsset* physicsAsset = characterMesh->GetPhysicsAsset();
mergedMesh->SetPhysicsAsset(physicsAsset);

// Copy the clothes.
CopyClothFromMesh(characterMesh, mergedMesh);

// Set the final mesh.
MeshComponent->SetSkeletalMesh( mergedMesh );
MeshComponent->bDisableClothSimulation = false;
MeshComponent->ClothTickFunction.bCanEverTick = true;`

Hi,

Any update?

Thanks.

You will have to call BindToSkeletalMesh() and probably set the section data, since otherwise your SkeletalMesh won’t know about the clothing asset it’s using, and it will just add a ClothingAsset to the list but not use it.

Here’s how it’s done in the SkeletalMesh editor:

`if (UClothingAssetCommon* ClothingAsset = Cast(InNewEntry->Asset.Get()))
{
ClothingAsset->Modify();

// Look for a currently bound asset an unbind it if necessary first
if (UClothingAssetBase* CurrentAsset = Mesh->GetSectionClothingAsset(InLodIdx, InSectionIdx))
{
CurrentAsset->Modify();
CurrentAsset->UnbindFromSkeletalMesh(Mesh, InLodIdx);
ClearOriginalSectionUserData();
}

if (!ClothingAsset->BindToSkeletalMesh(Mesh, InLodIdx, InSectionIdx, InNewEntry->AssetLodIndex))
{
// We failed to bind the clothing asset, reset box selection to “None”
SClothComboBoxPtr BoxPtr = ClothComboBoxes[BoxIndex];
if (BoxPtr.IsValid())
{
BoxPtr->SetSelectedItem(ClothingNoneEntry);
}
}
else
{
//Successful bind so set the SectionUserData
int32 AssetIndex = INDEX_NONE;
check(Mesh->GetMeshClothingAssets().Find(ClothingAsset, AssetIndex));
OriginalSectionData.CorrespondClothAssetIndex = static_cast(AssetIndex);
OriginalSectionData.ClothingData.AssetGuid = ClothingAsset->GetAssetGuid();
OriginalSectionData.ClothingData.AssetLodIndex = InNewEntry->AssetLodIndex;
}
}`

Passed the info along.

Thank you.