当前位置:   article > 正文

利用第三方后期处理材质(PostProcess Material)对物体进行描边【UE4】【C++】_ue4 c++ customdepth stencil value

ue4 c++ customdepth stencil value

 

效果图:

 

第一步,创建C++ Basic Code

 

第二步,定义键盘和鼠标输入的映射

 

第三步,修改 Rendering 中的 Custom Depth - Stencil Pass

 

第四步,找到GlobalPostProcessVolume [如果没有的话自行拖放一个PostProcessVolume组件] 

 

将 unbound 勾选上

 

再修改 Blendables 为 PPI_OutlineColored

 

 

完整代码如下:

MyPlayer.h

 

  1. // Fill out your copyright notice in the Description page of Project Settings.
  2. #pragma once
  3. #include "GameFramework/Character.h"
  4. #include "MyPlayer.generated.h"
  5. UCLASS()
  6. class OUTLINECPLUSPLUS_API AMyPlayer : public ACharacter
  7. {
  8. GENERATED_BODY()
  9. public:
  10. // Sets default values for this character's properties
  11. AMyPlayer();
  12. void MoveForward(float val);
  13. void MoveRight(float val);
  14. void LookYaw(float val);
  15. void LookPitch(float val);
  16. void Use();
  17. class AInteractableActor* FindFocusedActor();
  18. void HandleHighlight();
  19. // Called when the game starts or when spawned
  20. virtual void BeginPlay() override;
  21. // Called every frame
  22. virtual void Tick( float DeltaSeconds ) override;
  23. // Called to bind functionality to input
  24. virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override;
  25. private:
  26. UPROPERTY(EditDefaultsOnly)
  27. float InteractionDistance = 300.f; // 交互的范围
  28. class AInteractableActor* FocusedActor;
  29. // 用于 LineTraceSingleByChannel
  30. FCollisionQueryParams TraceParams;
  31. };

 

MyPlayer.cpp

 

 

 

  1. // Fill out your copyright notice in the Description page of Project Settings.
  2. #include "InteractableActor.h"
  3. #include "MyPlayer.h"
  4. // Sets default values
  5. AMyPlayer::AMyPlayer()
  6. {
  7. // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it.
  8. PrimaryActorTick.bCanEverTick = true;
  9. TraceParams = FCollisionQueryParams(FName(TEXT("TraceParams")), false, this);
  10. TraceParams.bTraceComplex = false;
  11. TraceParams.bTraceAsyncScene = false;
  12. TraceParams.bReturnPhysicalMaterial = false;
  13. }
  14. // Called when the game starts or when spawned
  15. void AMyPlayer::BeginPlay()
  16. {
  17. Super::BeginPlay();
  18. }
  19. // Called every frame
  20. void AMyPlayer::Tick( float DeltaTime )
  21. {
  22. Super::Tick( DeltaTime );
  23. if (Controller && Controller->IsLocalController())
  24. {
  25. HandleHighlight();
  26. }
  27. }
  28. // Called to bind functionality to input
  29. void AMyPlayer::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent)
  30. {
  31. Super::SetupPlayerInputComponent(PlayerInputComponent);
  32. InputComponent->BindAxis("MoveForward", this, &AMyPlayer::MoveForward);
  33. InputComponent->BindAxis("MoveRight", this, &AMyPlayer::MoveRight);
  34. InputComponent->BindAxis("LookYaw", this, &AMyPlayer::LookYaw);
  35. InputComponent->BindAxis("LookPitch", this, &AMyPlayer::LookPitch);
  36. InputComponent->BindAction("Use", IE_Pressed, this, &AMyPlayer::Use);
  37. }
  38. // 前后移动
  39. void AMyPlayer::MoveForward(float val)
  40. {
  41. FRotator Rotation(0, GetActorRotation().Yaw, 0); // Roll, Yaw, Pitch
  42. FVector forward = FRotationMatrix(Rotation).GetScaledAxis(EAxis::X);
  43. AddMovementInput(forward, val);
  44. }
  45. // 左右移动
  46. void AMyPlayer::MoveRight(float val)
  47. {
  48. FRotator Rotation(0, GetActorRotation().Yaw, 0); // Roll, Yaw, Pitch
  49. FVector right = FRotationMatrix(Rotation).GetScaledAxis(EAxis::Y);
  50. AddMovementInput(right, val);
  51. }
  52. // 左右转向
  53. void AMyPlayer::LookYaw(float val)
  54. {
  55. AddControllerYawInput(val);
  56. }
  57. // 上下转向
  58. void AMyPlayer::LookPitch(float val)
  59. {
  60. // 注意方向相反
  61. AddControllerPitchInput(val);
  62. }
  63. // 按 E 键与激活对象进行交互
  64. void AMyPlayer::Use()
  65. {
  66. AInteractableActor* Interactable = FindFocusedActor();
  67. if (Interactable)
  68. {
  69. // OnInteract_Implementation
  70. Interactable->OnInteract(this);
  71. }
  72. }
  73. AInteractableActor* AMyPlayer::FindFocusedActor()
  74. {
  75. if (!Controller)
  76. {
  77. return nullptr;
  78. }
  79. FVector Location;
  80. FRotator Rotation;
  81. FHitResult Hit(ForceInit);
  82. Controller->GetPlayerViewPoint(Location, Rotation);
  83. FVector Start = Location;
  84. FVector End = Start + (Rotation.Vector() * InteractionDistance);
  85. // 通过 “射线拾取” 选定对象
  86. GetWorld()->LineTraceSingleByChannel(Hit, Start, End, ECC_Camera, TraceParams);
  87. if (Hit.bBlockingHit) // 击中
  88. {
  89. // 获取当前被击中的对象的引用
  90. AInteractableActor* MyCastActor = Cast<AInteractableActor>(Hit.GetActor());
  91. if (MyCastActor)
  92. {
  93. return MyCastActor;
  94. }
  95. }
  96. return nullptr;
  97. }
  98. void AMyPlayer::HandleHighlight()
  99. {
  100. AInteractableActor* NewHighlight = FindFocusedActor();
  101. if (NewHighlight)
  102. {
  103. // 如果当前描边和新激活的对象不是同一个
  104. if (FocusedActor != NewHighlight)
  105. {
  106. if (FocusedActor)
  107. {
  108. // 当前描边对象取消描边
  109. FocusedActor->OnEndFocus();
  110. }
  111. // 描边新激活对象
  112. NewHighlight->OnBeginFocus();
  113. FocusedActor = NewHighlight;
  114. }
  115. }
  116. else
  117. {
  118. if (FocusedActor)
  119. {
  120. // 取消描边
  121. FocusedActor->OnEndFocus();
  122. FocusedActor = nullptr;
  123. }
  124. }
  125. }

 

 

 

InteractableActor.h

 

  1. // Fill out your copyright notice in the Description page of Project Settings.
  2. #pragma once
  3. #include "GameFramework/Actor.h"
  4. #include "OutlineCPlusPlus.h"
  5. #include "InteractableActor.generated.h"
  6. UCLASS()
  7. class OUTLINECPLUSPLUS_API AInteractableActor : public AActor
  8. {
  9. GENERATED_BODY()
  10. public:
  11. // Sets default values for this actor's properties
  12. AInteractableActor();
  13. // Called when the game starts or when spawned
  14. virtual void BeginPlay() override;
  15. // Called every frame
  16. virtual void Tick( float DeltaSeconds ) override;
  17. UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = Interaction)
  18. void OnInteract(AActor* Caller) ;
  19. virtual void OnInteract_Implementation(AActor* Caller);
  20. void OnBeginFocus();
  21. void OnEndFocus();
  22. private:
  23. UPROPERTY(EditDefaultsOnly)
  24. uint32 bCanInteract : 1;
  25. TArray<UMeshComponent*> Meshes;
  26. UPROPERTY(EditDefaultsOnly)
  27. EStencilColor Color = EStencilColor::SC_Green;
  28. };

 

InteractableActor.cpp

 

 

 

  1. // Fill out your copyright notice in the Description page of Project Settings.
  2. #include "MyPlayer.h"
  3. #include "InteractableActor.h"
  4. // Sets default values
  5. AInteractableActor::AInteractableActor()
  6. {
  7. // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it.
  8. PrimaryActorTick.bCanEverTick = true;
  9. }
  10. // Called when the game starts or when spawned
  11. void AInteractableActor::BeginPlay()
  12. {
  13. Super::BeginPlay();
  14. for (UActorComponent* Mesh : GetComponentsByClass(UMeshComponent::StaticClass()))
  15. {
  16. UMeshComponent* thisMesh = Cast<UMeshComponent>(Mesh);
  17. if (thisMesh)
  18. {
  19. Meshes.Push(thisMesh);
  20. }
  21. }
  22. }
  23. // Called every frame
  24. void AInteractableActor::Tick( float DeltaTime )
  25. {
  26. Super::Tick( DeltaTime );
  27. }
  28. void AInteractableActor::OnInteract_Implementation(AActor* Caller)
  29. {
  30. AMyPlayer* Player = Cast<AMyPlayer>(Caller);
  31. if (Player)
  32. {
  33. GEngine->AddOnScreenDebugMessage(-1,
  34. 5.f,
  35. FColor::Red,
  36. FString::Printf(TEXT("Now deleting the interactable actor! "))
  37. );
  38. // 销毁自己
  39. Destroy();
  40. }
  41. }
  42. void AInteractableActor::OnBeginFocus()
  43. {
  44. if (bCanInteract)
  45. {
  46. for (UMeshComponent* Mesh : Meshes)
  47. {
  48. Mesh->SetRenderCustomDepth(true);
  49. Mesh->SetCustomDepthStencilValue((uint8)Color);
  50. }
  51. }
  52. }
  53. void AInteractableActor::OnEndFocus()
  54. {
  55. if (bCanInteract)
  56. {
  57. for (UMeshComponent* Mesh : Meshes)
  58. {
  59. Mesh->SetRenderCustomDepth(false);
  60. }
  61. }
  62. }

 

 

 

颜色 的 Enum 

 

  1. UENUM(BlueprintType)
  2. enum class EStencilColor : uint8
  3. {
  4. SC_Green = 250 UMETA(DisplayName = "Green"),
  5. SC_Blue = 251 UMETA(DisplayName = "Blue"),
  6. SC_Red = 252 UMETA(DisplayName = "Red"),
  7. SC_White = 253 UMETA(DisplayName = "White")
  8. };

 

 

 

 

 

第三方材质下载链接

PostProcess 官方文档

 

 

 

 

 

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/羊村懒王/article/detail/101965
推荐阅读
相关标签
  

闽ICP备14008679号