Download

[Solved] Poseable Mesh goes into a T Stance

For our AI Character class, when they die, we ragdoll them, let the ragdoll settle, then spawn a poseablemesh class I call ACorpse to provide a lightweight corpse without having to keep the Character class alive. This works great up to a point. I’ve been scratching my head on the problem I ran into for over a day and I thought I better ask if anyone else has seen something like this.

First the blueprint for the character class gets an event to turn on physics, drop the AI’s weapon, let the ragdoll settle, then calls the C++ function to spawn the corpse and poke its mesh reference in to it so the socket copy can be done for the bone rotations. The Corpse class, on BeginPlay, locates its poseablemesh, sets the bone transforms and makes the new poseable mesh visible. After a couple of seconds, the AI class destroys itself and all that is left is the corpse. Works flawlessly. That is until I wanted to add corpse looting to it.

The problem appears when I parent the corpse class to our item class. The item class is just a wrapper to provide items to any Actor in our game. The idea is that with the item class in the hierarchy, the corpse class will then have some items which the player can loot. When I parent the corpse class to our item class, the poseablemesh T stances rather than the bone copy working correctly. The item class is rather simple, and just contains a list of items that can be picked up if the player looks at its either visible or invisible static mesh. It is not related to having the static mesh there since I’ve tested with having no item class static mesh and the results are the same.

The bottom line is I can only make the poseablemesh accept the bone transforms if I keep the actor class (containing the poseablemesh component) directly parented to AActor. Anyone know what might disturb the poseablemesh component in this manner?

Character Blueprint when AI Death is signaled:

Character class Corpse Spawner:


void AAICharacter::SpawnDestroyedActor() {

    UE_LOG(LogTemp,Error,TEXT("AICharacter: SpawnDestroyedActor has started"));

    if(DestroyedVersion != nullptr) {

        ACorpse* AICorpse;

        AICorpse = Cast<ACorpse>(SpawnBPDeferred<ACorpse>(GetWorld(), DestroyedVersion, this->GetActorLocation(), this->GetActorRotation()));

        AICorpse->MeshReference=MeshReference; //Poke the Mesh Ref into Corpse class to let it copy bone transforms

        AICorpse->FinishSpawning(this->GetActorTransform());

    } else {

        UE_LOG(LogTemp,Error,TEXT("AICharacter: Failed to find DestroyedVersion"));

    }

    FinalizeDeath(); //Destroy this AI

}


Corpse Class BeginPlay (no other code in this class):


void ACorpse::BeginPlay()

{

    UE_LOG(LogTemp,Warning,TEXT("Corpse: Beginning Corpse Bone Copy"));

    TArray<UPoseableMeshComponent*> comps;

    this->GetComponents<UPoseableMeshComponent>(comps);

    if(comps.Num()>0) {

        PoseableMeshReference=comps[0];

    } else {

        UE_LOG(LogTemp,Error,TEXT("Corpse: Failed to get poseable mesh component"));

    }

    TArray<FName> AllSockets = MeshReference->GetAllSocketNames();

    for(int32 i=0;i<AllSockets.Num();i++) {

        PoseableMeshReference->SetBoneTransformByName(AllSockets*, MeshReference->GetSocketTransform(AllSockets*),EBoneSpaces::WorldSpace);

        UE_LOG(LogTemp,Error,TEXT("Corpse: Setting socket name %s"),*AllSockets*.ToString());

    }

    Super::BeginPlay();

    PoseableMeshReference->SetHiddenInGame(false);

}


I found this problem myself. It was a stupid mistake in the intermediate item class I mention above. It’s BeginPlay was holding up the corpse class causing it to apparently set the bones after the AI class had destroyed. Surprising it didn’t abort nor put out an error.

I will leave the thread here in case someone new to unreal needs to know how to set up a corpse from their AIs. I found nothing on the net concerning the entire steps needed to do it with a poseable mesh. I will respond to any questions concerning that process if someone comes across this needing help.