六一的部落格


关关难过关关过,前路漫漫亦灿灿。




AController


切换Pawn

-
AController::Possess
AController::OnPossess

AController::Possess

切换到指定Pawn

 1/**
 2 * Handles attaching this controller to the specified pawn.
 3 * Only runs on the network authority (where HasAuthority() returns true).
 4 * Derived native classes can override OnPossess to filter the specified pawn.
 5 * When possessed pawn changed, blueprint class gets notified by ReceivePossess
 6 * and OnNewPawn delegate is broadcasted.
 7 * @param InPawn The Pawn to be possessed.
 8 * @see HasAuthority, OnPossess, ReceivePossess
 9 */
10UFUNCTION(BlueprintCallable, BlueprintAuthorityOnly, Category=Pawn, meta=(Keywords="set controller"))
11virtual void Possess(APawn* InPawn) final; // DEPRECATED(4.22, "Possess is marked virtual final as you should now be overriding OnPossess instead")

OnNewPawn委托通知客户端有两种情形:

  1. 新设置Pawn和当前Pawn不一致: RestartPlayer不满足
  2. 新设置Pawn和当前Pawn一致, 即可以通过控制器得到Pawn, 但新设置Pawn还无法获得Controller: RestartPlayer满足
 1void AController::Possess(APawn* InPawn)
 2{
 3    if (!bCanPossessWithoutAuthority && !HasAuthority())
 4    {
 5        FMessageLog("PIE").Warning(FText::Format(
 6            LOCTEXT("ControllerPossessAuthorityOnly", "Possess function should only be used by the network authority for {0}"),
 7            FText::FromName(GetFName())
 8            ));
 9        UE_LOG(LogController, Warning, TEXT("Trying to possess %s without network authority! Request will be ignored."), *GetNameSafe(InPawn));
10        return;
11    }
12
13    REDIRECT_OBJECT_TO_VLOG(InPawn, this);
14
15    APawn* CurrentPawn = GetPawn();
16
17    // A notification is required when the current assigned pawn is not possessed (i.e. pawn assigned before calling Possess)
18    const bool bNotificationRequired = (CurrentPawn != nullptr) && (CurrentPawn->GetController() == nullptr);
19
20    // To preserve backward compatibility we keep notifying derived classed for null pawn in case some
21    // overrides decided to react differently when asked to possess a null pawn.
22    // Default engine implementation is to unpossess the current pawn.
23    OnPossess(InPawn);
24
25    // Notify when pawn to possess (different than the assigned one) has been accepted by the native class or notification is explicitly required
26    APawn* NewPawn = GetPawn();
27    if ((NewPawn != CurrentPawn) || bNotificationRequired)
28    {
29        ReceivePossess(NewPawn);
30        OnNewPawn.Broadcast(NewPawn);
31        OnPossessedPawnChanged.Broadcast(bNotificationRequired ? nullptr : CurrentPawn, NewPawn);
32    }
33
34    TRACE_PAWN_POSSESS(this, InPawn); 
35}

AController::OnPossess

切换Pawn时被调用: 通过SetPawn使能通过控制器获得Pawn, 也设置Pawn的Controller, 使得可以通过Pawn获得Controller

1/**
2 * Overridable native function for when this controller is asked to possess a pawn.
3 * @param InPawn The Pawn to be possessed
4 */
5virtual void OnPossess(APawn* InPawn);
 1void AController::OnPossess(APawn* InPawn)
 2{
 3    const bool bNewPawn = GetPawn() != InPawn;
 4
 5    // Unpossess current pawn (if any) when current pawn changes
 6    if (bNewPawn && GetPawn() != nullptr)
 7    {
 8        UnPossess();
 9    }
10
11    if (InPawn == nullptr)
12    {
13        return;
14    }
15
16    if (InPawn->Controller != nullptr)
17    {
18        UE_CLOG(InPawn->Controller == this, LogController, Warning, TEXT("Asking %s to possess pawn %s more than once; pawn will be restarted! Should call Unpossess first."), *GetNameSafe(this), *GetNameSafe(InPawn));
19        InPawn->Controller->UnPossess();
20    }
21
22    InPawn->PossessedBy(this);
23    SetPawn(InPawn);
24
25    // update rotation to match possessed pawn's rotation
26    SetControlRotation(Pawn->GetActorRotation());
27
28    Pawn->DispatchRestart(false);
29}

AController::SetPawn

设置控制器当前Pawn

1/** Setter for Pawn. Normally should only be used internally when possessing/unpossessing a Pawn. */
2virtual void SetPawn(APawn* InPawn);

AController::GetPawn

访问当前Pawn

1// Getter for Pawn
2FORCEINLINE APawn* GetPawn() const { return Pawn; }

AController::GetPawn<T>

访问当前Pawn

1// Templated version of GetPawn, will return nullptr if cast fails
2template<class T>
3T* GetPawn() const
4{
5    return Cast<T>(Pawn);
6}

AController::GetPlayerViewPoint

 1// *
 2// * Returns Player's Point of View
 3// * For the AI this means the Pawn's 'Eyes' ViewPoint
 4// * For a Human player, this means the Camera's ViewPoint
 5// *
 6// * @output	out_Location, view location of player
 7// * @output	out_rotation, view rotation of player
 8// *
 9UFUNCTION(BlueprintCallable, Category = Pawn)
10virtual void GetPlayerViewPoint( FVector& Location, FRotator& Rotation ) const;      

Controller类



AController


切换Pawn

-
AController::Possess
AController::OnPossess

AController::Possess

切换到指定Pawn

 1/**
 2 * Handles attaching this controller to the specified pawn.
 3 * Only runs on the network authority (where HasAuthority() returns true).
 4 * Derived native classes can override OnPossess to filter the specified pawn.
 5 * When possessed pawn changed, blueprint class gets notified by ReceivePossess
 6 * and OnNewPawn delegate is broadcasted.
 7 * @param InPawn The Pawn to be possessed.
 8 * @see HasAuthority, OnPossess, ReceivePossess
 9 */
10UFUNCTION(BlueprintCallable, BlueprintAuthorityOnly, Category=Pawn, meta=(Keywords="set controller"))
11virtual void Possess(APawn* InPawn) final; // DEPRECATED(4.22, "Possess is marked virtual final as you should now be overriding OnPossess instead")

OnNewPawn委托通知客户端有两种情形:

  1. 新设置Pawn和当前Pawn不一致: RestartPlayer不满足
  2. 新设置Pawn和当前Pawn一致, 即可以通过控制器得到Pawn, 但新设置Pawn还无法获得Controller: RestartPlayer满足
 1void AController::Possess(APawn* InPawn)
 2{
 3    if (!bCanPossessWithoutAuthority && !HasAuthority())
 4    {
 5        FMessageLog("PIE").Warning(FText::Format(
 6            LOCTEXT("ControllerPossessAuthorityOnly", "Possess function should only be used by the network authority for {0}"),
 7            FText::FromName(GetFName())
 8            ));
 9        UE_LOG(LogController, Warning, TEXT("Trying to possess %s without network authority! Request will be ignored."), *GetNameSafe(InPawn));
10        return;
11    }
12
13    REDIRECT_OBJECT_TO_VLOG(InPawn, this);
14
15    APawn* CurrentPawn = GetPawn();
16
17    // A notification is required when the current assigned pawn is not possessed (i.e. pawn assigned before calling Possess)
18    const bool bNotificationRequired = (CurrentPawn != nullptr) && (CurrentPawn->GetController() == nullptr);
19
20    // To preserve backward compatibility we keep notifying derived classed for null pawn in case some
21    // overrides decided to react differently when asked to possess a null pawn.
22    // Default engine implementation is to unpossess the current pawn.
23    OnPossess(InPawn);
24
25    // Notify when pawn to possess (different than the assigned one) has been accepted by the native class or notification is explicitly required
26    APawn* NewPawn = GetPawn();
27    if ((NewPawn != CurrentPawn) || bNotificationRequired)
28    {
29        ReceivePossess(NewPawn);
30        OnNewPawn.Broadcast(NewPawn);
31        OnPossessedPawnChanged.Broadcast(bNotificationRequired ? nullptr : CurrentPawn, NewPawn);
32    }
33
34    TRACE_PAWN_POSSESS(this, InPawn); 
35}

AController::OnPossess

切换Pawn时被调用: 通过SetPawn使能通过控制器获得Pawn, 也设置Pawn的Controller, 使得可以通过Pawn获得Controller

1/**
2 * Overridable native function for when this controller is asked to possess a pawn.
3 * @param InPawn The Pawn to be possessed
4 */
5virtual void OnPossess(APawn* InPawn);
 1void AController::OnPossess(APawn* InPawn)
 2{
 3    const bool bNewPawn = GetPawn() != InPawn;
 4
 5    // Unpossess current pawn (if any) when current pawn changes
 6    if (bNewPawn && GetPawn() != nullptr)
 7    {
 8        UnPossess();
 9    }
10
11    if (InPawn == nullptr)
12    {
13        return;
14    }
15
16    if (InPawn->Controller != nullptr)
17    {
18        UE_CLOG(InPawn->Controller == this, LogController, Warning, TEXT("Asking %s to possess pawn %s more than once; pawn will be restarted! Should call Unpossess first."), *GetNameSafe(this), *GetNameSafe(InPawn));
19        InPawn->Controller->UnPossess();
20    }
21
22    InPawn->PossessedBy(this);
23    SetPawn(InPawn);
24
25    // update rotation to match possessed pawn's rotation
26    SetControlRotation(Pawn->GetActorRotation());
27
28    Pawn->DispatchRestart(false);
29}

AController::SetPawn

设置控制器当前Pawn

1/** Setter for Pawn. Normally should only be used internally when possessing/unpossessing a Pawn. */
2virtual void SetPawn(APawn* InPawn);

AController::GetPawn

访问当前Pawn

1// Getter for Pawn
2FORCEINLINE APawn* GetPawn() const { return Pawn; }

AController::GetPawn<T>

访问当前Pawn

1// Templated version of GetPawn, will return nullptr if cast fails
2template<class T>
3T* GetPawn() const
4{
5    return Cast<T>(Pawn);
6}

AController::GetPlayerViewPoint

 1// *
 2// * Returns Player's Point of View
 3// * For the AI this means the Pawn's 'Eyes' ViewPoint
 4// * For a Human player, this means the Camera's ViewPoint
 5// *
 6// * @output	out_Location, view location of player
 7// * @output	out_rotation, view rotation of player
 8// *
 9UFUNCTION(BlueprintCallable, Category = Pawn)
10virtual void GetPlayerViewPoint( FVector& Location, FRotator& Rotation ) const;