本文整理汇总了C++中FHitResult::GetComponent方法的典型用法代码示例。如果您正苦于以下问题:C++ FHitResult::GetComponent方法的具体用法?C++ FHitResult::GetComponent怎么用?C++ FHitResult::GetComponent使用的例子?那么, 这里精选的方法代码示例或许可以为您提供帮助。您也可以进一步了解该方法所在类FHitResult
的用法示例。
在下文中一共展示了FHitResult::GetComponent方法的13个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1: RMouseDownSelectTarget
void ALMPlayerController::RMouseDownSelectTarget()
{
FHitResult HitRes = FHitResult();
TArray<TEnumAsByte<EObjectTypeQuery>> ObjectType;
//只检测一下对象
ObjectType.Add(EOBJECTTYPEQUERY_SELECTACTOR);
if (GetHitResultUnderCursorForObjects(ObjectType,false,HitRes))
{
if (HitRes.GetComponent() == pCurSelectedComponent)
{
return;
}
else
{
if (pCurSelectedComponent != nullptr)
pCurSelectedComponent->SetRenderCustomDepth(false);
pCurSelectedComponent = HitRes.GetComponent();
pCurSelectedComponent->SetRenderCustomDepth(true);
}
}
}
示例2: Interact
void AKIMCharacter::Interact() {
if (IsInRoationState && PickedUpItem) {
((AKIMInteractionActor*)PickedUpItem)->LayBack(this);
return;
}
FHitResult outHit;
FCollisionQueryParams params;
params.AddIgnoredActor(this);
params.AddIgnoredActor(PickedUpItem);
FVector TraceStart = CameraComponent->GetComponentLocation();
FVector TraceEnd = TraceStart + (CameraComponent->GetForwardVector() * InteractionDistance);
GetWorld()->LineTraceSingleByChannel(outHit, TraceStart, TraceEnd, ECollisionChannel::ECC_PhysicsBody, params);
if (outHit.GetActor() != NULL && outHit.GetActor()->GetClass()->IsChildOf(AKIMInteractionActor::StaticClass())) {
AKIMInteractionActor* InteractionActor = ((AKIMInteractionActor*)outHit.GetActor());
InteractionActor->Interacted(this, outHit.GetComponent());
UE_LOG(LogClass, Warning, TEXT("Interacted with %s"), *outHit.GetActor()->GetName());
UE_LOG(LogClass, Warning, TEXT("(%s)"), *outHit.GetComponent()->GetName());
}
else if (outHit.GetActor() == NULL && PickedUpItem) {
PickedUpItem->DetachRootComponentFromParent(true);
((AKIMInteractionActor*)PickedUpItem)->Droped();
((AKIMInteractionActor*)PickedUpItem)->InteractionType = EKIMInteractionTypes::OnPickUp;
UE_LOG(LogClass, Warning, TEXT("Droped %s"), *PickedUpItem->GetName());
PickedUpItem = NULL;
}
}
示例3: ActivateButton
//USE BUTTON CODE//
void APlayerCharacter::ActivateButton()
{
UPeterAnimInstance* PeterAnimInstance = Cast<UPeterAnimInstance>(GetMesh()->GetAnimInstance());
if (PeterAnimInstance)
{
PeterAnimInstance->bIsInteracting = true;
}
if (PhysicsHandleActive)
{
PhysicsHandleActive = false;
}
else if (!PhysicsHandleActive)
{
PhysicsHandleActive = true;
}
bool TraceSuccess;
FHitResult OutHit;
//Uses Trace Channel: PlayerTrace
TraceSuccess = this->TraceFromSelf(OutHit, 300.f, ECollisionChannel::ECC_GameTraceChannel6);
if (TraceSuccess)
{
AInteractable* InteractableObject = NULL;
InteractableObject = Cast<AInteractable>(OutHit.GetActor());
if (Cast<ALiftableBox>(OutHit.GetActor()))
{
if (PhysicsHandleActive)
{
PickedUpBox = Cast<ALiftableBox>(OutHit.GetActor());
if (PickedUpBox->bIsAbove(this) && PickedUpBox->CanBeLifted == true)
{
PhysicsHandler->GrabComponent(OutHit.GetComponent(), OutHit.BoneName, OutHit.Location, true);
}
}
return;
}
else if (InteractableObject && InteractableObject->GetClass()->IsChildOf(ALightSwitch::StaticClass()) == false)
{
if (FVector::Dist(GetActorLocation(), InteractableObject->GetActorLocation()) < 250)
{
InteractableObject->Interact(this);
}
}
}
}
示例4: OnFire
void AFP_FirstPersonCharacter::OnFire()
{
// Play a sound if there is one
if (FireSound != NULL)
{
UGameplayStatics::PlaySoundAtLocation(this, FireSound, GetActorLocation());
}
// try and play a firing animation if specified
if(FireAnimation != NULL)
{
// Get the animation object for the arms mesh
UAnimInstance* AnimInstance = Mesh1P->GetAnimInstance();
if(AnimInstance != NULL)
{
AnimInstance->Montage_Play(FireAnimation, 1.f);
}
}
// Now send a trace from the end of our gun to see if we should hit anything
APlayerController* PlayerController = Cast<APlayerController>(GetController());
// Calculate the direction of fire and the start location for trace
FVector CamLoc;
FRotator CamRot;
PlayerController->GetPlayerViewPoint(CamLoc, CamRot);
const FVector ShootDir = CamRot.Vector();
FVector StartTrace = FVector::ZeroVector;
if (PlayerController)
{
FRotator UnusedRot;
PlayerController->GetPlayerViewPoint(StartTrace, UnusedRot);
// Adjust trace so there is nothing blocking the ray between the camera and the pawn, and calculate distance from adjusted start
StartTrace = StartTrace + ShootDir * ((GetActorLocation() - StartTrace) | ShootDir);
}
// Calculate endpoint of trace
const FVector EndTrace = StartTrace + ShootDir * WeaponRange;
// Check for impact
const FHitResult Impact = WeaponTrace(StartTrace, EndTrace);
// Deal with impact
AActor* DamagedActor = Impact.GetActor();
UPrimitiveComponent* DamagedComponent = Impact.GetComponent();
// If we hit an actor, with a component that is simulating physics, apply an impulse
if ((DamagedActor != NULL) && (DamagedActor != this) && (DamagedComponent != NULL) && DamagedComponent->IsSimulatingPhysics())
{
DamagedComponent->AddImpulseAtLocation(ShootDir*WeaponDamage, Impact.Location);
}
}
示例5: UpdatePortalSearch
void AMagnetTile::UpdatePortalSearch( AActor* actor , const FHitResult& hit )
{
auto portal = Cast<APortalTile>( actor );
if ( portal != nullptr && CanSpawnSubMagnet() )
{
auto hitPortalTrigger = hit.GetComponent();
FVector subMagnetTileDir , subMagnetTilePos;
portal->GetMagnetPortalTransportedLocation( hitPortalTrigger , subMagnetTileDir , subMagnetTilePos );
SpawnSubMagnet( subMagnetTilePos , subMagnetTileDir );
}
}
示例6: Grab
void UGrabber::Grab()
{
UE_LOG(LogTemp, Warning, TEXT("Grab!!"));
FHitResult hitResult = GetFirstPhysicsBodyInReach();
auto ActorHit = hitResult.GetActor();
if (ActorHit != nullptr) {
auto ComponentToGrab = hitResult.GetComponent();
//Try and reach any actors with physics body and then attach them
physicsHandle->GrabComponent(ComponentToGrab, NAME_None, ComponentToGrab->GetOwner()->GetActorLocation(), true);
}
}
示例7: GrabPressed
///Define the press grab key operation
void UGrabber::GrabPressed() {
UE_LOG(LogTemp, Warning, TEXT("Grab Pressed!"));
// Get the hit object with physical body
FHitResult HitObj = FindTheFirstReachingObject();
auto GrabObjComponent = HitObj.GetComponent();
auto GrabObjActor = HitObj.GetActor();
// If hit a object, grab it by using grab component
if (GrabObjActor) {
PhysicalHandler->GrabComponent(
GrabObjComponent,
NAME_None,
GrabObjComponent->GetOwner()->GetActorLocation(),
true
);
}
}
示例8: SpawnImpactFX
void AProjectile::SpawnImpactFX(const FHitResult& Hit)
{
FRandomStream Stream; //random stream
FRotator rotTemp = Hit.ImpactNormal.Rotation();
rotTemp = FRotator(rotTemp.Pitch, rotTemp.Yaw, Stream.FRandRange(-180, 180)); //randomly rotate the effect
//impact effects sound spawn
UGameplayStatics::SpawnEmitterAtLocation(this, ImpactFX.Effect, Hit.ImpactPoint, rotTemp, true);
//spawn decal effect on impact position
UGameplayStatics::SpawnDecalAttached(ImpactFX.DecalMaterial,
FVector(ImpactFX.DecalSize, ImpactFX.DecalSize, 1.0F),
Hit.GetComponent(),
Hit.BoneName,
Hit.ImpactPoint,
rotTemp,
EAttachLocation::KeepWorldPosition, ImpactFX.DecalHealth);
}
示例9: GetSpringCollision
UPrimitiveComponent* UPhysicsSpringComponent::GetSpringCollision(const FVector& Start, const FVector& End, float& Time) const
{
UWorld* World = GetWorld();
AActor* IgnoreActor = bIgnoreSelf ? GetOwner() : nullptr;
static FName NAME_Spring = FName(TEXT("SpringComponent"));
FCollisionQueryParams QueryParams(NAME_Spring, true, IgnoreActor);
FHitResult Hit;
UPrimitiveComponent* CollidedComponent = nullptr;
const FVector Delta = End - Start;
const float DeltaSizeSqr = Delta.SizeSquared();
if (DeltaSizeSqr > FMath::Square(SMALL_NUMBER))
{
if (bool bBlockingHit = World->SweepSingleByChannel(Hit, Start, End, FQuat::Identity, SpringChannel, FCollisionShape::MakeSphere(SpringRadius), QueryParams))
{
CollidedComponent = Hit.GetComponent();
Time = CollidedComponent ? Hit.Time : 1.f;
}
}
return CollidedComponent;
}
示例10: ConvertQueryImpactHit
EConvertQueryResult ConvertQueryImpactHit(const UWorld* World, const PxLocationHit& PHit, FHitResult& OutResult, float CheckLength, const PxFilterData& QueryFilter, const FVector& StartLoc, const FVector& EndLoc, const PxGeometry* const Geom, const PxTransform& QueryTM, bool bReturnFaceIndex, bool bReturnPhysMat)
{
SCOPE_CYCLE_COUNTER(STAT_ConvertQueryImpactHit);
#if WITH_EDITOR
if(bReturnFaceIndex && World->IsGameWorld())
{
if(!ensure(UPhysicsSettings::Get()->bSuppressFaceRemapTable == false))
{
UE_LOG(LogPhysics, Error, TEXT("A scene query is relying on face indices, but bSuppressFaceRemapTable is true."));
bReturnFaceIndex = false;
}
}
#endif
checkSlow(PHit.flags & PxHitFlag::eDISTANCE);
const bool bInitialOverlap = PHit.hadInitialOverlap();
if (bInitialOverlap && Geom != nullptr)
{
ConvertOverlappedShapeToImpactHit(World, PHit, StartLoc, EndLoc, OutResult, *Geom, QueryTM, QueryFilter, bReturnPhysMat);
return EConvertQueryResult::Valid;
}
// See if this is a 'blocking' hit
const PxFilterData PShapeFilter = PHit.shape->getQueryFilterData();
const PxQueryHitType::Enum HitType = FPxQueryFilterCallback::CalcQueryHitType(QueryFilter, PShapeFilter);
OutResult.bBlockingHit = (HitType == PxQueryHitType::eBLOCK);
OutResult.bStartPenetrating = bInitialOverlap;
// calculate the hit time
const float HitTime = PHit.distance/CheckLength;
OutResult.Time = HitTime;
OutResult.Distance = PHit.distance;
// figure out where the the "safe" location for this shape is by moving from the startLoc toward the ImpactPoint
const FVector TraceStartToEnd = EndLoc - StartLoc;
const FVector SafeLocationToFitShape = StartLoc + (HitTime * TraceStartToEnd);
OutResult.Location = SafeLocationToFitShape;
const bool bUsePxPoint = ((PHit.flags & PxHitFlag::ePOSITION) && !bInitialOverlap);
if (bUsePxPoint && !PHit.position.isFinite())
{
#if ENABLE_NAN_DIAGNOSTIC
SetHitResultFromShapeAndFaceIndex(PHit.shape, PHit.actor, PHit.faceIndex, OutResult, bReturnPhysMat);
UE_LOG(LogCore, Error, TEXT("ConvertQueryImpactHit() NaN details:\n>> Actor:%s (%s)\n>> Component:%s\n>> Item:%d\n>> BoneName:%s\n>> Time:%f\n>> Distance:%f\n>> Location:%s\n>> bIsBlocking:%d\n>> bStartPenetrating:%d"),
*GetNameSafe(OutResult.GetActor()), OutResult.Actor.IsValid() ? *OutResult.GetActor()->GetPathName() : TEXT("no path"),
*GetNameSafe(OutResult.GetComponent()), OutResult.Item, *OutResult.BoneName.ToString(),
OutResult.Time, OutResult.Distance, *OutResult.Location.ToString(), OutResult.bBlockingHit ? 1 : 0, OutResult.bStartPenetrating ? 1 : 0);
#endif // ENABLE_NAN_DIAGNOSTIC
OutResult.Reset();
logOrEnsureNanError(TEXT("ConvertQueryImpactHit() received NaN/Inf for position: %.2f %.2f %.2f"), PHit.position.x, PHit.position.y, PHit.position.z);
return EConvertQueryResult::Invalid;
}
OutResult.ImpactPoint = bUsePxPoint ? P2UVector(PHit.position) : StartLoc;
// Caution: we may still have an initial overlap, but with null Geom. This is the case for RayCast results.
const bool bUsePxNormal = ((PHit.flags & PxHitFlag::eNORMAL) && !bInitialOverlap);
if (bUsePxNormal && !PHit.normal.isFinite())
{
#if ENABLE_NAN_DIAGNOSTIC
SetHitResultFromShapeAndFaceIndex(PHit.shape, PHit.actor, PHit.faceIndex, OutResult, bReturnPhysMat);
UE_LOG(LogCore, Error, TEXT("ConvertQueryImpactHit() NaN details:\n>> Actor:%s (%s)\n>> Component:%s\n>> Item:%d\n>> BoneName:%s\n>> Time:%f\n>> Distance:%f\n>> Location:%s\n>> bIsBlocking:%d\n>> bStartPenetrating:%d"),
*GetNameSafe(OutResult.GetActor()), OutResult.Actor.IsValid() ? *OutResult.GetActor()->GetPathName() : TEXT("no path"),
*GetNameSafe(OutResult.GetComponent()), OutResult.Item, *OutResult.BoneName.ToString(),
OutResult.Time, OutResult.Distance, *OutResult.Location.ToString(), OutResult.bBlockingHit ? 1 : 0, OutResult.bStartPenetrating ? 1 : 0);
#endif // ENABLE_NAN_DIAGNOSTIC
OutResult.Reset();
logOrEnsureNanError(TEXT("ConvertQueryImpactHit() received NaN/Inf for normal: %.2f %.2f %.2f"), PHit.normal.x, PHit.normal.y, PHit.normal.z);
return EConvertQueryResult::Invalid;
}
FVector Normal = bUsePxNormal ? P2UVector(PHit.normal).GetSafeNormal() : -TraceStartToEnd.GetSafeNormal();
OutResult.Normal = Normal;
OutResult.ImpactNormal = Normal;
OutResult.TraceStart = StartLoc;
OutResult.TraceEnd = EndLoc;
#if ENABLE_CHECK_HIT_NORMAL
CheckHitResultNormal(OutResult, TEXT("Invalid Normal from ConvertQueryImpactHit"), StartLoc, EndLoc, Geom);
#endif // ENABLE_CHECK_HIT_NORMAL
if (bUsePxNormal && !Normal.IsNormalized())
{
// TraceStartToEnd should never be zero, because of the length restriction in the raycast and sweep tests.
Normal = -TraceStartToEnd.GetSafeNormal();
OutResult.Normal = Normal;
OutResult.ImpactNormal = Normal;
}
const PxGeometryType::Enum SweptGeometryType = Geom ? Geom->getType() : PxGeometryType::eINVALID;
OutResult.ImpactNormal = FindGeomOpposingNormal(SweptGeometryType, PHit, TraceStartToEnd, Normal);
// Fill in Actor, Component, material, etc.
SetHitResultFromShapeAndFaceIndex(PHit.shape, PHit.actor, PHit.faceIndex, OutResult, bReturnPhysMat);
//.........这里部分代码省略.........
示例11: ResolvePenetrationImpl
bool UMovementComponent::ResolvePenetrationImpl(const FVector& ProposedAdjustment, const FHitResult& Hit, const FQuat& NewRotationQuat)
{
// SceneComponent can't be in penetration, so this function really only applies to PrimitiveComponent.
const FVector Adjustment = ConstrainDirectionToPlane(ProposedAdjustment);
if (!Adjustment.IsZero() && UpdatedPrimitive)
{
// See if we can fit at the adjusted location without overlapping anything.
AActor* ActorOwner = UpdatedComponent->GetOwner();
if (!ActorOwner)
{
return false;
}
UE_LOG(LogMovement, Verbose, TEXT("ResolvePenetration: %s.%s at location %s inside %s.%s at location %s by %.3f (netmode: %d)"),
*ActorOwner->GetName(),
*UpdatedComponent->GetName(),
*UpdatedComponent->GetComponentLocation().ToString(),
*GetNameSafe(Hit.GetActor()),
*GetNameSafe(Hit.GetComponent()),
Hit.Component.IsValid() ? *Hit.GetComponent()->GetComponentLocation().ToString() : TEXT("<unknown>"),
Hit.PenetrationDepth,
(uint32)GetNetMode());
// We really want to make sure that precision differences or differences between the overlap test and sweep tests don't put us into another overlap,
// so make the overlap test a bit more restrictive.
const float OverlapInflation = CVarPenetrationOverlapCheckInflation.GetValueOnGameThread();
bool bEncroached = OverlapTest(Hit.TraceStart + Adjustment, NewRotationQuat, UpdatedPrimitive->GetCollisionObjectType(), UpdatedPrimitive->GetCollisionShape(OverlapInflation), ActorOwner);
if (!bEncroached)
{
// Move without sweeping.
MoveUpdatedComponent(Adjustment, NewRotationQuat, false, nullptr, ETeleportType::TeleportPhysics);
UE_LOG(LogMovement, Verbose, TEXT("ResolvePenetration: teleport by %s"), *Adjustment.ToString());
return true;
}
else
{
// Disable MOVECOMP_NeverIgnoreBlockingOverlaps if it is enabled, otherwise we wouldn't be able to sweep out of the object to fix the penetration.
TGuardValue<EMoveComponentFlags> ScopedFlagRestore(MoveComponentFlags, EMoveComponentFlags(MoveComponentFlags & (~MOVECOMP_NeverIgnoreBlockingOverlaps)));
// Try sweeping as far as possible...
FHitResult SweepOutHit(1.f);
bool bMoved = MoveUpdatedComponent(Adjustment, NewRotationQuat, true, &SweepOutHit, ETeleportType::TeleportPhysics);
UE_LOG(LogMovement, Verbose, TEXT("ResolvePenetration: sweep by %s (success = %d)"), *Adjustment.ToString(), bMoved);
// Still stuck?
if (!bMoved && SweepOutHit.bStartPenetrating)
{
// Combine two MTD results to get a new direction that gets out of multiple surfaces.
const FVector SecondMTD = GetPenetrationAdjustment(SweepOutHit);
const FVector CombinedMTD = Adjustment + SecondMTD;
if (SecondMTD != Adjustment && !CombinedMTD.IsZero())
{
bMoved = MoveUpdatedComponent(CombinedMTD, NewRotationQuat, true, nullptr, ETeleportType::TeleportPhysics);
UE_LOG(LogMovement, Verbose, TEXT("ResolvePenetration: sweep by %s (MTD combo success = %d)"), *CombinedMTD.ToString(), bMoved);
}
}
// Still stuck?
if (!bMoved)
{
// Try moving the proposed adjustment plus the attempted move direction. This can sometimes get out of penetrations with multiple objects
const FVector MoveDelta = ConstrainDirectionToPlane(Hit.TraceEnd - Hit.TraceStart);
if (!MoveDelta.IsZero())
{
bMoved = MoveUpdatedComponent(Adjustment + MoveDelta, NewRotationQuat, true, nullptr, ETeleportType::TeleportPhysics);
UE_LOG(LogMovement, Verbose, TEXT("ResolvePenetration: sweep by %s (adjusted attempt success = %d)"), *(Adjustment + MoveDelta).ToString(), bMoved);
}
}
return bMoved;
}
}
return false;
}
示例12: TickComponent
void UShardsMovementComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction)
{
Super::TickComponent(DeltaTime, TickType, ThisTickFunction);
FHitResult HitResult;
FHitResult ShapeTraceResult;
FCollisionShape shape = FCollisionShape::MakeBox(FVector(0.72f*playerradius, 0.72f*playerradius,10.0f));
FCollisionQueryParams Params;
Params.bFindInitialOverlaps = true;
Params.AddIgnoredActor(UpdatedComponent->GetAttachmentRootActor());
// Telepads don't count.
for (TActorIterator<ATelePad> ActorItr(GetWorld()); ActorItr; ++ActorItr) {
Params.AddIgnoredActor(ActorItr.operator->());
}
// Neither do destructibles.
for (TActorIterator<ADestructibleBox> ActorItr(GetWorld()); ActorItr; ++ActorItr) {
// When they're broken, that is.
if (ActorItr->fadetimer >= 0.0f) {
Params.AddIgnoredActor(ActorItr.operator->());
}
}
if (isclimbing) {
return;
}
TArray<FHitResult> results;
if (forceregiondirection.Z == 0.0f) {
GetWorld()->SweepMultiByChannel(results, UpdatedComponent->GetComponentLocation() - 0.0f*45.0f*FVector::UpVector, UpdatedComponent->GetComponentLocation() - 1000.0f*FVector::UpVector, FQuat::Identity, ECC_Visibility, shape, Params); //100
for (FHitResult r : results) {
if (r.Normal.Z > 0.6f) {
ShapeTraceResult = r;
break;
}
}
if (!ShapeTraceResult.IsValidBlockingHit()) {
GetWorld()->LineTraceSingleByChannel(ShapeTraceResult, UpdatedComponent->GetComponentLocation(), UpdatedComponent->GetComponentLocation() - 1000.0f*FVector::UpVector, ECC_Visibility, Params);
}
}
FVector PlayerCapsuleBottom = UpdatedComponent->GetComponentLocation() - 45.0f * FVector::UpVector; // 50
float RequiredDistance = (onground ? 50.0f*grounddetecttfudgefactor : 10.0f)*FMath::Pow(playerhalfheight / 90.0f,4.0f) + playerhalfheight/2.0f; //50,1
DistanceFromImpact = (PlayerCapsuleBottom - ShapeTraceResult.ImpactPoint).Z;
overground = ShapeTraceResult.IsValidBlockingHit();
FHitResult groundhitresult;
GetWorld()->LineTraceSingleByChannel(groundhitresult, UpdatedComponent->GetComponentLocation(), UpdatedComponent->GetComponentLocation() - 10000.0f*FVector::UpVector, ECC_Visibility, Params);
groundtracehit = groundhitresult.ImpactPoint;
if (!onground) {
offGroundTime += DeltaTime;
}
toosteep = false;
if (enforcementtimer >= 0.0f) {
enforcementtimer += DeltaTime;
toosteep = true;
}
wasonground = onground;
onground = false;
prevgroundvelocity = groundvelocity;
groundvelocity = FVector::ZeroVector;
platformangularfrequency = 0.0f;
platformspindir = 1;
FloorNormal = FVector::ZeroVector;
if ((enforcementtimer < timerlimit && ShapeTraceResult.Normal.Z>0.6f) && DistanceFromImpact < RequiredDistance && !justjumped) { // (PlayerVelocity.Z <= 0.0f || wasonground)
if (ShapeTraceResult.Normal.Z < minnormalz) {
if (enforcementtimer == -1.0f) {
enforcementtimer = 0.0f;
}
} else {
enforcementtimer = -1.0f;
}
FVector pvel;
// Handle moving platforms.
if (ShapeTraceResult.GetActor() != nullptr && ShapeTraceResult.GetComponent() != nullptr && ShapeTraceResult.GetComponent()->IsA(UStaticMeshComponent::StaticClass())) {
// The motion of a point on a rigid body is the combination of its motion about the center of mass...
FVector angvel = FMath::DegreesToRadians((((UStaticMeshComponent*)ShapeTraceResult.GetComponent())->GetPhysicsAngularVelocity()));
FVector rr = GetActorLocation() - (((UStaticMeshComponent*)ShapeTraceResult.GetComponent())->GetComponentLocation());
FVector rvel = FVector::CrossProduct(angvel, rr);
// ...and the motion of the center of mass itself.
FVector cmvel = (((UStaticMeshComponent*)ShapeTraceResult.GetComponent())->GetPhysicsLinearVelocity());
groundvelocity = rvel + cmvel;
platformangularfrequency = -angvel.Z;
}
if ((PlayerVelocity.Z <= groundvelocity.Z || wasonground)) {
onground = true;
offGroundTime = 0.0f;
}
}
//.........这里部分代码省略.........
示例13: checkLaserCollisions
//.........这里部分代码省略.........
isFrame = true;
}
}
//cut the laser length to make sure new sub laser start doesn't hit the same object
if (typeFound && CanSpawnSubLaser()) SpawnSubLaser(hit.ImpactPoint + hit.ImpactNormal * 10.0f, hit.ImpactNormal);
}
//if sub laser already exists then keep updating its rotation and position
auto subLaserExistsHitDeflectiveTile = currentDepth < MAX_DEPTH && nextLaser != nullptr && tile != nullptr;
if (subLaserExistsHitDeflectiveTile)
{
auto incomingVector = hit.ImpactPoint - GetActorLocation();
//if the incoming vector's angle is too small then kill sublasers to avoid laser flickering
auto dot = FVector::DotProduct(-incomingVector.GetSafeNormal(), hit.ImpactNormal);
auto angle = FMath::RadiansToDegrees(FMath::Acos(dot));
if (angle < 70.0f)
{
auto newDir = FMath::GetReflectionVector(incomingVector, hit.ImpactNormal);
auto start = hit.ImpactPoint + newDir * 2.0f;
nextLaser->SetActorLocation(hit.ImpactPoint);
nextLaser->dir = newDir.IsNormalized() ? newDir : newDir.GetSafeNormal();
nextLaser->laserParticle->EmitterInstances[0]->SetBeamSourcePoint(hit.ImpactPoint, 0);
nextLaser->laserParticle->EmitterInstances[0]->SetBeamTargetPoint(start + newDir * length, 0);
}
else
{
KillSubLaser();
}
}
//if the laser hits turret then kills it
if (!typeFound)
{
auto turret = Cast<ATurretPawn>(hitActor);
if (turret != nullptr)
{
typeFound = true;
turret->Damage(2.0f);
}
}
APortalTile* portal = nullptr;
if (!typeFound)
{
portal = Cast<APortalTile>(hitActor);
if (CanSpawnSubLaser() && portal != nullptr)
{
typeFound = true;
auto relativePos = hit.ImpactPoint - hit.GetComponent()->GetComponentLocation();
currHitPoint = relativePos + portal->GetActorLocation();
SpawnSubLaser(currHitPoint, hit.ImpactNormal);
}
}
auto subLaserExistsHitPortalTile = currentDepth < MAX_DEPTH && nextLaser != nullptr && portal != nullptr;
if (subLaserExistsHitPortalTile)
{
FVector newSourcePos;
portal->GetLaserPortalTransportedLocation(hit.GetComponent(), nextLaser->dir, newSourcePos);
nextLaser->SetActorLocation(newSourcePos);
nextLaser->laserParticle->EmitterInstances[0]->SetBeamSourcePoint(newSourcePos, 0);
nextLaser->laserParticle->EmitterInstances[0]->SetBeamTargetPoint(newSourcePos + nextLaser->dir * length, 0);
}
bool notHitDeflectiveTile = tile == nullptr || isFrame;
bool notHitPortal = portal == nullptr;
if (notHitDeflectiveTile && notHitPortal)
{
KillSubLaser();
}
}
laserSparkParticle->SetWorldLocation(currHitPoint);
laserSparkParticle->SetWorldRotation(FVector(currHitPoint -
GetActorLocation()).GetSafeNormal().Rotation().Quaternion());
}
else
{
currHitPoint = laserVector;
laserEmitter->SetBeamTargetPoint(pos + currHitPoint, 0);
laserSparkParticle->SetWorldLocation( pos + currHitPoint );
laserSparkParticle->SetWorldRotation( FVector( (pos + currHitPoint) -
GetActorLocation() ).GetSafeNormal().Rotation().Quaternion() );
KillSubLaser();
}
//only root laser can have an emitter mesh
if (currentDepth != 0)
{
//update laser emitter rotation
mesh->SetVisibility(false);
}
else
{
mesh->SetWorldRotation(dir.Rotation());
}
}