Why is the pawn sometimes destroyed after the ragdoll?

Sometimes the pawn is destroyed automatically.
I’m simulating a respawn. But I don’t destroy the actor.

1-First I change the collision settings on the mesh and the capsule (Ragdoll).
2-I wait five seconds
3-Restored mesh and capsule collisions
4-I attach the mesh to the capsule
5-Teleport to respawn point

Most of the time this works correctly. But sometimes the pawn is destroyed while I wait the five seconds.

Does anyone know why this happens?



This is the capsule collisions configuration:


Capsule (Alive):

void UCharacterCapsuleComponent::Alive()
{	
	SetNotifyRigidBodyCollision(true);
	SetGenerateOverlapEvents(true);
	CanCharacterStepUpOn = ECanBeCharacterBase::ECB_No;
	SetCollisionEnabled( ECollisionEnabled::QueryAndPhysics);
	SetCollisionResponseToAllChannels(ECollisionResponse::ECR_Block);
	SetCollisionResponseToChannel(ECollisionChannel::ECC_Pawn,	ECollisionResponse::ECR_Block);
	SetCollisionResponseToChannel( ECollisionChannel::ECC_Visibility,	ECollisionResponse::ECR_Ignore);
	SetCollisionResponseToChannel( ECollisionChannel::ECC_Camera,	ECollisionResponse::ECR_Ignore);
	SetSimulatePhysics(false);	
}

Capsule (Ragdoll)

void UCharacterCapsuleComponent::Dead() 
{	
	SetNotifyRigidBodyCollision(false);
	SetGenerateOverlapEvents(false);
	CanCharacterStepUpOn = ECanBeCharacterBase::ECB_Yes;
	SetCollisionEnabled( ECollisionEnabled::NoCollision );	
	SetCollisionResponseToAllChannels(ECollisionResponse::ECR_Ignore);	
}

This is the mesh collisions configuration:


Mesh (Alive):

void UCharacterSkeletalMehs::Alive()
{	
	SetGenerateOverlapEvents(true);
	CanCharacterStepUpOn = ECanBeCharacterBase::ECB_No;
	SetCollisionEnabled( ECollisionEnabled::QueryAndPhysics);
	SetCollisionObjectType( ECollisionChannel::ECC_Pawn );
	
	
	SetCollisionResponseToAllChannels(ECollisionResponse::ECR_Block);
	SetCollisionResponseToChannel( ECollisionChannel::ECC_Pawn, ECollisionResponse::ECR_Ignore);
	SetCollisionResponseToChannel( ECollisionChannel::ECC_WorldDynamic, ECollisionResponse::ECR_Ignore);
	SetCollisionResponseToChannel( ECollisionChannel::ECC_Camera, ECollisionResponse::ECR_Ignore);

	SetSimulatePhysics(false);
}

Mesh (Ragdoll)


void UCharacterSkeletalMehs::Dead()
{	
	SetGenerateOverlapEvents(false);
	CanCharacterStepUpOn = ECanBeCharacterBase::ECB_Yes;
	SetCollisionEnabled( ECollisionEnabled::PhysicsOnly );
	SetCollisionObjectType( ECollisionChannel::ECC_Pawn );
	SetCollisionResponseToAllChannels(ECollisionResponse::ECR_Ignore);
	SetCollisionResponseToChannel( ECollisionChannel::ECC_WorldStatic, ECollisionResponse::ECR_Block);
	SetAllBodiesSimulatePhysics(true);			
}

Restore the pawn:


void UCharacterSkeletalMehs::Restore()
{	
	AActor* TheOwner = GetOwner();
	if (!IsValid(TheOwner)) return;
	

	const ACharacter *Character = Cast<ACharacter>(TheOwner);
	if (!IsValid(Character)) return;
	

	UCapsuleComponent* CapsuleComponent = Character->GetCapsuleComponent();
	if (!IsValid(CapsuleComponent))  return;

	const FAttachmentTransformRules AttachmentRules = FAttachmentTransformRules
	(
		EAttachmentRule::KeepRelative,
		EAttachmentRule::KeepRelative,
		EAttachmentRule::KeepRelative,
		false
	);
	
	if (!AttachToComponent(CapsuleComponent, AttachmentRules)) return;

	TheOwner->SetActorTransform(ActorTransform, false,	nullptr, ETeleportType::TeleportPhysics  );
	SetRelativeTransform(MeshTransform,false,	nullptr,  ETeleportType::TeleportPhysics );	
}

Thank you so much!!

This seems to work.
Seems like the pawn is no longer destroyed on death.

Following Lyra’s example I added this to my code at the time of death.


For movement component:

const ACharacter* TheOwner = GetOwner<ACharacter>();
if (!IsValid(TheOwner))return;	

UCharacterMovementComponent* MoveComp = CastChecked<UCharacterMovementComponent>(TheOwner->GetCharacterMovement());
if (!IsValid(MoveComp)) return;		
	
MoveComp->StopMovementImmediately();
MoveComp->SetComponentTickEnabled(false)

For the skeletal mesh:

WakeAllRigidBodies();
bBlendPhysics = true;

However I’m not sure why this actually works.
As it only happened with NPCs, I suppose there was some task moving the pawn at the moment of death. And StopMovementImmediately(); cancels the AIMoveTo() task.
So at the end of the day I think AIMoveTo() was to blame for everything.

They are just assumptions.
I would like to know what was really happening.
If you know, please post it here.

Thank you so much!!


This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.