FVector ABaseController::GetHitPosition() { FNavLocation location; UNavigationSystem* navSys = UNavigationSystem::GetCurrent(World); navSys->GetRandomPointInNavigableRadius(AttackLocation, 200.f, location); return location.Location; }
FVector ABaseController::GetNewWanderPosition() { FNavLocation Location; UNavigationSystem* NavSys = World->GetNavigationSystem(); FHitResult hit(ForceInit); FCollisionQueryParams traceParams = FCollisionQueryParams(FName(TEXT("RV_Trace")), true, Self); traceParams.bTraceComplex = true; traceParams.bTraceAsyncScene = true; int times = 0; float minimuimDist = Self->MinimuimDistanceBetweenWanderLocations; do{ if (times >= 50) { times = 0; minimuimDist -= 500.f; } times++; NavSys->GetRandomPointInNavigableRadius(Self->GetActorLocation(), Self->SightRange, Location); } while (FVector::Dist(Location.Location, Self->GetActorLocation()) < minimuimDist); bool bHit = World->LineTraceSingleByChannel(hit, Self->EyeLocation, Location.Location, ECC_Visibility, traceParams); return Location.Location; }
FVector ABaseController::GetNewSearchPosition() { FNavLocation Location; UNavigationSystem* NavSys = World->GetNavigationSystem(); NavSys->GetRandomPointInNavigableRadius(TargetsLastKnownPosition, Self->SearchRange, Location); return Location.Location; }
void ANavLinkProxy::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) { bool bUpdateInNavOctree = false; if (PropertyChangedEvent.Property && PropertyChangedEvent.Property->GetFName() == GET_MEMBER_NAME_CHECKED(ANavLinkProxy, bSmartLinkIsRelevant)) { SmartLinkComp->SetNavigationRelevancy(bSmartLinkIsRelevant); bUpdateInNavOctree = true; } const FName CategoryName = FObjectEditorUtils::GetCategoryFName(PropertyChangedEvent.Property); const FName MemberCategoryName = FObjectEditorUtils::GetCategoryFName(PropertyChangedEvent.MemberProperty); if (CategoryName == TEXT("SimpleLink") || MemberCategoryName == TEXT("SimpleLink")) { bUpdateInNavOctree = true; } if (bUpdateInNavOctree) { UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys) { NavSys->UpdateActorInNavOctree(*this); } } Super::PostEditChangeProperty(PropertyChangedEvent); }
FAIRequestID AAIController::RequestPathAndMove(FPathFindingQuery& Query, AActor* Goal, float AcceptanceRadius, bool bStopOnOverlap, FCustomMoveSharedPtr CustomData) { FAIRequestID RequestID; UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys) { FPathFindingResult PathResult = NavSys->FindPathSync(Query); if (PathResult.Result != ENavigationQueryResult::Error) { if (PathResult.IsSuccessful() && PathResult.Path.IsValid()) { if (Goal) { PathResult.Path->SetGoalActorObservation(*Goal, 100.0f); } PathResult.Path->EnableRecalculationOnInvalidation(true); } RequestID = RequestMove(PathResult.Path, Goal, AcceptanceRadius, bStopOnOverlap, CustomData); } else { UE_VLOG(this, LogBehaviorTree, Error, TEXT("Trying to find path to %s resulted in Error"), *GetNameSafe(Goal)); } } return RequestID; }
FORCENOINLINE #endif // NAVSYS_DEBUG void FNavigationOctreeSemantics::SetElementId(const FNavigationOctreeElement& Element, FOctreeElementId Id) { UWorld* World = NULL; UObject* ElementOwner = Element.GetOwner(); if (AActor* Actor = Cast<AActor>(ElementOwner)) { World = Actor->GetWorld(); } else if (UActorComponent* AC = Cast<UActorComponent>(ElementOwner)) { World = AC->GetWorld(); } else if (ULevel* Level = Cast<ULevel>(ElementOwner)) { World = Level->OwningWorld; } UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(World); if (NavSys) { NavSys->SetObjectsNavOctreeId(ElementOwner, Id); } }
FAIRequestID AAIController::RequestPathAndMove(const FAIMoveRequest& MoveRequest, FPathFindingQuery& Query) { FAIRequestID RequestID; UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys) { FPathFindingResult PathResult = NavSys->FindPathSync(Query); if (PathResult.Result != ENavigationQueryResult::Error) { if (PathResult.IsSuccessful() && PathResult.Path.IsValid()) { if (MoveRequest.IsUsingPathfinding()) { if (MoveRequest.HasGoalActor()) { PathResult.Path->SetGoalActorObservation(*MoveRequest.GetGoalActor(), 100.0f); } PathResult.Path->EnableRecalculationOnInvalidation(true); } RequestID = RequestMove(MoveRequest, PathResult.Path); } } else { UE_VLOG(this, LogAINavigation, Error, TEXT("Trying to find path to %s resulted in Error"), *GetNameSafe(MoveRequest.GetGoalActor())); } } return RequestID; }
void AAIController::FindPathForMoveRequest(const FAIMoveRequest& MoveRequest, FPathFindingQuery& Query, FNavPathSharedPtr& OutPath) const { SCOPE_CYCLE_COUNTER(STAT_AI_Overall); UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys) { FPathFindingResult PathResult = NavSys->FindPathSync(Query); if (PathResult.Result != ENavigationQueryResult::Error) { if (PathResult.IsSuccessful() && PathResult.Path.IsValid()) { if (MoveRequest.IsMoveToActorRequest()) { PathResult.Path->SetGoalActorObservation(*MoveRequest.GetGoalActor(), 100.0f); } PathResult.Path->EnableRecalculationOnInvalidation(true); OutPath = PathResult.Path; } } else { UE_VLOG(this, LogAINavigation, Error, TEXT("Trying to find path to %s resulted in Error") , MoveRequest.IsMoveToActorRequest() ? *GetNameSafe(MoveRequest.GetGoalActor()) : *MoveRequest.GetGoalLocation().ToString()); UE_VLOG_SEGMENT(this, LogAINavigation, Error, GetPawn() ? GetPawn()->GetActorLocation() : FAISystem::InvalidLocation , MoveRequest.GetGoalLocation(), FColor::Red, TEXT("Failed move to %s"), *GetNameSafe(MoveRequest.GetGoalActor())); } } }
void UCheatManager::RebuildNavigation() { UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys) { NavSys->Build(); } }
void UNavLinkCustomComponent::SetDisabledArea(TSubclassOf<UNavArea> AreaClass) { DisabledAreaClass = AreaClass; if (IsNavigationRelevant() && !bLinkEnabled && GetWorld() != nullptr ) { UNavigationSystem* NavSys = GetWorld()->GetNavigationSystem(); NavSys->UpdateCustomLink(this); } }
// execution EBTNodeResult::Type UAIE_GoToRandom_BTTaskNode::ExecuteTask(UBehaviorTreeComponent& OwnerComp, uint8* NodeMemory) { /* call super * should aquire refrences for our BehaviorTreeComp, BlackboardComp, AIController, and BotCharacter * will return EBTNodeResult::Succeeded if we have all of them * will return EBTNodeResult::Failed if it failed to grab any of them */ EBTNodeResult::Type resultFromSuperExecution = Super::ExecuteTask(OwnerComp, NodeMemory); // check that we successfully grabbed the BehaviorTreeComp, BlackboardComp, AIController, and BotCharacter if (resultFromSuperExecution == EBTNodeResult::Succeeded) { // check that we can get the World if (GetWorld()) { // get the current nav system from the world UNavigationSystem* navSystem = UNavigationSystem::GetCurrent(GetWorld()); // check that we have a nav system if (navSystem) { // get our actors current location to pe used as our start position FVector startPosi = BotCharacter->GetActorLocation(); // create a nav location to be used as our end position // default will be set to our current position in case of failure to find a suitable end position FNavLocation endPosi = FNavLocation(startPosi); // attempt to get a random new position if (navSystem->GetRandomReachablePointInRadius(startPosi, searchRadius, endPosi)) { // if we were successfull in finding a new location get the MoveToLocation BlackboardKeyID FBlackboard::FKey BlackboardKey_MoveToLocation = Blackboard->GetKeyID("MoveToLocation"); // check that we got the key if ( Blackboard->IsValidKey( BlackboardKey_MoveToLocation)) { // set the MoveToLocation BlackboardKeyID to our new location Blackboard->SetValue<UBlackboardKeyType_Vector>(BlackboardKey_MoveToLocation, endPosi.Location); // return succeeded now that we have set up our new loacation return EBTNodeResult::Succeeded; } else { // return Aborted if we can't find the Key as it will never succeed without a proper Key if (bForceSuccess) { return EBTNodeResult::Succeeded; } return EBTNodeResult::Aborted; } } // return in progress if their are currently no valid locations if (bForceSuccess) { return EBTNodeResult::Succeeded; } return EBTNodeResult::InProgress; } } } // we will only get here if execution fails so we will check if force success is on if (bForceSuccess) { // if force success is on we will return Succeeded anyway return EBTNodeResult::Succeeded; } // we want to return Failed after the force success check return EBTNodeResult::Failed; }
void USmartNavLinkComponent::SetDisabledArea(TSubclassOf<class UNavArea> AreaClass) { DisabledAreaClass = AreaClass; if (IsNavigationRelevant() && !bLinkEnabled) { UNavigationSystem* NavSys = GetWorld()->GetNavigationSystem(); NavSys->UpdateSmartLink(this); } }
void UNavLinkCustomComponent::SetEnabledArea(TSubclassOf<class UNavArea> AreaClass) { EnabledAreaClass = AreaClass; if (IsNavigationRelevant() && bLinkEnabled) { UNavigationSystem* NavSys = GetWorld()->GetNavigationSystem(); NavSys->UpdateCustomLink(this); } }
bool UGameplayDebuggingComponent::ServerCollectNavmeshData_Validate(FVector_NetQuantize10 TargetLocation) { bool bIsValid = false; #if WITH_RECAST UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); bIsValid = NavSys && NavSys->GetMainNavData(FNavigationSystem::DontCreate); #endif return bIsValid; }
void USmartNavLinkComponent::OnOwnerUnregistered() { if (GetOwner() == NULL || GetWorld() == NULL || GetWorld()->GetNavigationSystem() == NULL) { return; } // always try to unregister, even if not relevant right now UNavigationSystem* NavSys = GetWorld()->GetNavigationSystem(); NavSys->UnregisterSmartLink(this); }
void ANavigationTestingActor::SearchPathTo(ANavigationTestingActor* Goal) { #if WITH_EDITORONLY_DATA if (EdRenderComp) { EdRenderComp->MarkRenderStateDirty(); } #endif // WITH_EDITORONLY_DATA if (Goal == NULL) { return; } UNavigationSystem* NavSys = GetWorld()->GetNavigationSystem(); check(NavSys); const double StartTime = FPlatformTime::Seconds(); FPathFindingQuery Query = BuildPathFindingQuery(Goal); EPathFindingMode::Type Mode = bUseHierarchicalPathfinding ? EPathFindingMode::Hierarchical : EPathFindingMode::Regular; FPathFindingResult Result = NavSys->FindPathSync(NavAgentProps, Query, Mode); const double EndTime = FPlatformTime::Seconds(); const float Duration = (EndTime - StartTime); PathfindingTime = Duration * 1000000.0f; // in micro seconds [us] bPathIsPartial = Result.IsPartial(); bPathExist = Result.IsSuccessful(); bPathSearchOutOfNodes = bPathExist ? Result.Path->DidSearchReachedLimit() : false; LastPath = Result.Path; PathCost = bPathExist ? Result.Path->GetCost() : 0.0f; if (bPathExist) { LastPath->AddObserver(PathObserver); if (OffsetFromCornersDistance > 0.0f) { ((FNavMeshPath*)LastPath.Get())->OffsetFromCorners(OffsetFromCornersDistance); } } #if WITH_RECAST && WITH_EDITORONLY_DATA if (bGatherDetailedInfo && !bUseHierarchicalPathfinding) { ARecastNavMesh* RecastNavMesh = Cast<ARecastNavMesh>(MyNavData); if (RecastNavMesh && RecastNavMesh->HasValidNavmesh()) { PathfindingSteps = RecastNavMesh->DebugPathfinding(Query, DebugSteps); } } #endif }
void ANavMeshBoundsVolume::PostLoad() { Super::PostLoad(); #if WITH_NAVIGATION_GENERATOR UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys && Role == ROLE_Authority) { NavSys->OnNavigationBoundsUpdated(this); } #endif }
void UNavLinkCustomComponent::OnUnregister() { Super::OnUnregister(); UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys == NULL) { return; } // always try to unregister, even if not relevant right now NavSys->UnregisterCustomLink(this); }
void ANavigationTestingActor::TickMe() { UNavigationSystem* NavSys = GetWorld() ? GetWorld()->GetNavigationSystem() : NULL; if (NavSys && !NavSys->IsNavigationBuildInProgress()) { #if WITH_RECAST && WITH_EDITORONLY_DATA delete TickHelper; TickHelper = NULL; #endif UpdatePathfinding(); } }
void UNavigationQueryFilter::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) { Super::PostEditChangeProperty(PropertyChangedEvent); // remove cached filter settings from existing NavigationSystems for (const FWorldContext& Context : GEngine->GetWorldContexts()) { UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(Context.World()); if (NavSys) { NavSys->ResetCachedFilter(GetClass()); } } }
void USmartNavLinkComponent::OnOwnerRegistered() { if (GetOwner() == NULL || GetWorld() == NULL || GetWorld()->GetNavigationSystem() == NULL) { return; } UNavigationSystem* NavSys = GetWorld()->GetNavigationSystem(); if (NavLinkUserId == 0) { NavLinkUserId = NavSys->FindFreeSmartLinkId(); } NavSys->RegisterSmartLink(this); }
void ANavMeshBoundsVolume::PostEditChangeProperty( struct FPropertyChangedEvent& PropertyChangedEvent) { Super::PostEditChangeProperty(PropertyChangedEvent); #if WITH_NAVIGATION_GENERATOR UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (GIsEditor && NavSys) { if (PropertyChangedEvent.Property == NULL || PropertyChangedEvent.Property->GetFName() == GET_MEMBER_NAME_CHECKED(ABrush, BrushBuilder)) { NavSys->OnNavigationBoundsUpdated(this); } } #endif // WITH_NAVIGATION_GENERATOR }
EBTNodeResult::Type UATBTTask_MoveArea::ExecuteTask(UBehaviorTreeComponent& OwnerComp, uint8* NodeMemory) { UNavigationSystem* NavigationSystem = UNavigationSystem::GetCurrent(GetWorld()); AATCharacterAI* MyCharacter = Cast<AATCharacterAI>(OwnerComp.GetAIOwner()->GetPawn()); if (NavigationSystem != nullptr && MyCharacter != nullptr) { FNavLocation RandomPointIn; if (NavigationSystem->GetRandomPointInNavigableRadius(MyCharacter->GetActorLocation(), MyCharacter->AreaRadius, RandomPointIn)) { OwnerComp.GetBlackboardComponent()->SetValue<UBlackboardKeyType_Vector>(GetSelectedBlackboardKey(), RandomPointIn.Location); return EBTNodeResult::Succeeded; } } return EBTNodeResult::Failed; }
void UNavMovementComponent::UpdateNavAgent(const UCapsuleComponent& CapsuleComponent) { if (ShouldUpdateNavAgentWithOwnersCollision() == false) { return; } // initialize properties from navigation system UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys != nullptr) { NavAgentProps.NavWalkingSearchHeightScale = NavSys->GetDefaultSupportedAgentConfig().NavWalkingSearchHeightScale; } NavAgentProps.AgentRadius = CapsuleComponent.GetScaledCapsuleRadius(); NavAgentProps.AgentHeight = CapsuleComponent.GetScaledCapsuleHalfHeight() * 2.f; }
void UNavLinkCustomComponent::OnRegister() { Super::OnRegister(); UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys == NULL) { return; } if (NavLinkUserId == 0) { NavLinkUserId = INavLinkCustomInterface::GetUniqueId(); } NavSys->RegisterCustomLink(this); }
void FGameplayDebuggerCategory_Navmesh::CollectData(APlayerController* OwnerPC, AActor* DebugActor) { #if WITH_RECAST ARecastNavMesh* NavData = nullptr; APawn* PlayerPawn = OwnerPC ? OwnerPC->GetPawnOrSpectator() : nullptr; APawn* DebugActorAsPawn = Cast<APawn>(DebugActor); APawn* DestPawn = DebugActorAsPawn ? DebugActorAsPawn : PlayerPawn; if (DestPawn) { UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(OwnerPC->GetWorld()); const FNavAgentProperties& NavAgentProperties = DestPawn->GetNavAgentPropertiesRef(); NavData = Cast<ARecastNavMesh>(NavSys->GetNavDataForProps(NavAgentProperties)); } if (NavData) { // add 3x3 neighborhood of target const FVector TargetLocation = DestPawn->GetActorLocation(); TArray<int32> TileSet; int32 TileX = 0; int32 TileY = 0; const int32 DeltaX[] = { 0, 1, 1, 0, -1, -1, -1, 0, 1 }; const int32 DeltaY[] = { 0, 0, 1, 1, 1, 0, -1, -1, -1 }; int32 TargetTileX = 0; int32 TargetTileY = 0; NavData->GetNavMeshTileXY(TargetLocation, TargetTileX, TargetTileY); for (int32 Idx = 0; Idx < ARRAY_COUNT(DeltaX); Idx++) { const int32 NeiX = TargetTileX + DeltaX[Idx]; const int32 NeiY = TargetTileY + DeltaY[Idx]; NavData->GetNavMeshTilesAt(NeiX, NeiY, TileSet); } const int32 DetailFlags = (1 << static_cast<int32>(ENavMeshDetailFlags::PolyEdges)) | (1 << static_cast<int32>(ENavMeshDetailFlags::FilledPolys)) | (1 << static_cast<int32>(ENavMeshDetailFlags::NavLinks)); NavmeshRenderData.GatherData(NavData, DetailFlags, TileSet); } #endif // WITH_RECAST }
bool AAIController::BuildPathfindingQuery(const FAIMoveRequest& MoveRequest, FPathFindingQuery& Query) const { bool bResult = false; UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); const ANavigationData* NavData = (NavSys == nullptr) ? nullptr : MoveRequest.IsUsingPathfinding() ? NavSys->GetNavDataForProps(GetNavAgentPropertiesRef()) : NavSys->GetAbstractNavData(); if (NavData) { FVector GoalLocation = MoveRequest.GetGoalLocation(); if (MoveRequest.IsMoveToActorRequest()) { const INavAgentInterface* NavGoal = Cast<const INavAgentInterface>(MoveRequest.GetGoalActor()); if (NavGoal) { const FVector Offset = NavGoal->GetMoveGoalOffset(this); GoalLocation = FQuatRotationTranslationMatrix(MoveRequest.GetGoalActor()->GetActorQuat(), NavGoal->GetNavAgentLocation()).TransformPosition(Offset); } else { GoalLocation = MoveRequest.GetGoalActor()->GetActorLocation(); } } FSharedConstNavQueryFilter NavFilter = UNavigationQueryFilter::GetQueryFilter(*NavData, this, MoveRequest.GetNavigationFilter()); Query = FPathFindingQuery(*this, *NavData, GetNavAgentLocation(), GoalLocation, NavFilter); Query.SetAllowPartialPaths(MoveRequest.IsUsingPartialPaths()); if (PathFollowingComponent) { PathFollowingComponent->OnPathfindingQuery(Query); } bResult = true; } else { UE_VLOG(this, LogAINavigation, Warning, TEXT("Unable to find NavigationData instance while calling AAIController::BuildPathfindingQuery")); } return bResult; }
void UNavigationInvokerComponent::RegisterWithNavigationSystem(UNavigationSystem& NavSys) { if (IsActive()) { AActor* Owner = GetOwner(); if (Owner) { NavSys.RegisterInvoker(*Owner, TileGenerationRadius, TileRemovalRadius); } } }
void UNavigationComponent::OnSmartLinkBroadcast(class USmartNavLinkComponent* NearbyLink) { // update only when agent is actually moving if (NearbyLink == NULL || !Path.IsValid() || PathFollowComp == NULL || PathFollowComp->GetStatus() == EPathFollowingStatus::Idle) { return; } UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys == NULL || MyNavAgent == NULL || GetNavData() == NULL) { return; } const bool bHasLink = Path->ContainsSmartLink(NearbyLink); const bool bIsEnabled = NearbyLink->IsEnabled(); if (bIsEnabled == bHasLink) { // enabled link, path already use it - or - disabled link and path it's not using it return; } const FVector GoalLocation = Path->PathPoints.Last().Location; FPathFindingResult Result = NavSys->FindPathSync(*MyNavAgent->GetNavAgentProperties(), FPathFindingQuery(GetNavData(), MyNavAgent->GetNavAgentLocation(), GoalLocation, StoredQueryFilter), bDoHierarchicalPathfinding ? EPathFindingMode::Hierarchical : EPathFindingMode::Regular); if (Result.IsSuccessful() || Result.IsPartial()) { const bool bNewHasLink = Result.Path->ContainsSmartLink(NearbyLink); if ((bIsEnabled && !bHasLink && bNewHasLink) || (!bIsEnabled && bHasLink && !bNewHasLink)) { SetPath(Result.Path); NotifyPathUpdate(); } } }
void UNavMovementComponent::UpdateNavAgent(const AActor& Owner) { ensure(&Owner == GetOwner()); if (ShouldUpdateNavAgentWithOwnersCollision() == false) { return; } // initialize properties from navigation system UNavigationSystem* NavSys = UNavigationSystem::GetCurrent(GetWorld()); if (NavSys != nullptr) { NavAgentProps.NavWalkingSearchHeightScale = NavSys->GetDefaultSupportedAgentConfig().NavWalkingSearchHeightScale; } // Can't call GetSimpleCollisionCylinder(), because no components will be registered. float BoundRadius, BoundHalfHeight; Owner.GetSimpleCollisionCylinder(BoundRadius, BoundHalfHeight); NavAgentProps.AgentRadius = BoundRadius; NavAgentProps.AgentHeight = BoundHalfHeight * 2.f; }