今天要製作魔法攻擊的功能,大概的概念是在敵人腳下產生向上爆發的魔力衝擊,造成傷害並將敵人擊飛。
void AMagicWeapon::DoMagicStuff()
{
if (MeshMissile == nullptr) return;
FHitResult HitResult_v;
bool hit_v;
float LaunchForce = 700.f;
if (OwnerChar->TargetActor == nullptr)
{
float AttackRange=500;
float AttackDepth=500;
float MagicWidth=50;
FHitResult HitResult_h;
FCollisionQueryParams Params;
Params.AddIgnoredActor(MeshMissile.GetDefaultObject());
FVector Start = OwnerChar->GetActorLocation();
FVector End = OwnerChar->GetActorLocation() + OwnerChar->GetActorForwardVector()*AttackRange;
bool hit_h = GetWorld()->LineTraceSingleByChannel(
HitResult_h,
Start,
End,
ECC_Visibility,
Params
);
DrawDebugLine(
GetWorld(),
Start,
hit_h ? HitResult_h.ImpactPoint : End,
hit_h ? FColor::Green : FColor::Red,
false,
5,
0,
2
);
//FHitResult HitResult_v;
FVector vStart = HitResult_h.ImpactPoint + HitResult_h.ImpactNormal*MagicWidth;
hit_v = GetWorld()->LineTraceSingleByChannel(
HitResult_v,
hit_h ? vStart : End,
hit_h ? vStart + vStart.UpVector*(-AttackDepth) : End + End.UpVector*(-AttackDepth),
ECC_Visibility,
Params
);
DrawDebugLine(
GetWorld(),
hit_h ? vStart : End,
hit_v ? HitResult_v.ImpactPoint : End + End.UpVector*(-AttackDepth),
hit_v ? FColor::Green : FColor::Red,
false,
5,
0,
2
);
}else
{
AActor* TargetA = OwnerChar->TargetActor;
hit_v = true;
HitResult_v.ImpactPoint = TargetA->GetActorLocation();
}
if (hit_v)
{
FActorSpawnParameters SpawnParams;
SpawnParams.Owner = this;
SpawnParams.Instigator = OwnerChar;
GetWorld()->SpawnActor<AActor>(MeshMissile, HitResult_v.ImpactPoint, FRotator::ZeroRotator, SpawnParams);
TArray<FHitResult> AHitResult;
float Radius = 100.f;
DrawDebugSphere(GetWorld(), HitResult_v.ImpactPoint, Radius, 12, FColor::Red, false, 2, 2);
FCollisionQueryParams sParams;
sParams.AddIgnoredActor(OwnerChar);
sParams.AddIgnoredActor(this);
bool AHit = GetWorld()->SweepMultiByObjectType(
AHitResult,
HitResult_v.ImpactPoint,
HitResult_v.ImpactPoint,
FQuat::Identity, // no rotation for sphere
ECC_Pawn, // collision channel
FCollisionShape::MakeSphere(Radius), // << sphere shape
sParams
);
if (AHit)
for (auto sHitResult : AHitResult)
{
DrawDebugSphere(GetWorld(), sHitResult.ImpactPoint, 20, 8, FColor::Green, false, 2, 2);
if (AActor* HitActor = sHitResult.GetActor())
{
if (UHealthComponent* HealthComp = HitActor->FindComponentByTag<UHealthComponent>("Damage"))
{
HealthComp->ApplyDamage(10.f, HitActor, sHitResult, WeaponType);
if (ACharacter* Char = Cast<ACharacter>(HitActor))
Char->LaunchCharacter(FVector(0,0,LaunchForce), true, true);
else
if (sHitResult.GetComponent()->IsSimulatingPhysics())
sHitResult.GetComponent()->AddImpulse(FVector(0,0,LaunchForce), NAME_None, true);
}
}
}
}
}