// Copyright Ngonart OU. All Rights Reserved. // UE5 Modular Game Framework — PlanarCaptureCameraUtils // Static math library for mirror reflection, portal relative transform, // oblique projection, screen coverage, and visibility computations. // All functions are BlueprintCallable and use UE5's FMatrix/FVector/FPlane types. #pragma once #include "CoreMinimal.h" #include "Kismet/BlueprintFunctionLibrary.h" #include "PlanarCaptureCameraUtils.generated.h" /** * Static math library for planar capture camera transforms. * * Mirror: reflect the viewer camera across the mirror plane. * Portal: compute the relative transform from source surface to target surface. * All math happens in C++ for performance — Blueprint calls these as pure functions. */ UCLASS() class PG_FRAMEWORK_API UPlanarCaptureCameraUtils : public UBlueprintFunctionLibrary { GENERATED_BODY() public: // ======================================================================== // Mirror Reflection Math // ======================================================================== /** * Compute the mirrored camera transform for a planar mirror. * Reflects the viewer's camera position and rotation across the mirror plane. * * @param ViewerCameraTransform World transform of the viewer's camera. * @param MirrorPlaneTransform World transform of the mirror surface (XY plane, Z = normal). * @return The world transform for the SceneCapture camera. */ UFUNCTION(BlueprintCallable, BlueprintPure, Category = "Capture|CameraUtils") static FTransform ComputeMirroredTransform( const FTransform& ViewerCameraTransform, const FTransform& MirrorPlaneTransform); // ======================================================================== // Portal Relative Math // ======================================================================== /** * Compute the capture camera transform for a portal. * The viewer's position relative to the source surface is mapped to the * target surface's coordinate space. * * @param ViewerCameraTransform World transform of the viewer's camera. * @param SourceSurfaceTransform World transform of the portal entry surface. * @param TargetSurfaceTransform World transform of the portal exit surface. * @return The world transform for the SceneCapture camera. */ UFUNCTION(BlueprintCallable, BlueprintPure, Category = "Capture|CameraUtils") static FTransform ComputePortalTransform( const FTransform& ViewerCameraTransform, const FTransform& SourceSurfaceTransform, const FTransform& TargetSurfaceTransform); // ======================================================================== // Oblique Near-Plane Projection // ======================================================================== /** * Compute an oblique near-clip-plane projection matrix. * Used to prevent geometry behind the portal/mirror surface from clipping * into the capture view. * * @param FOV Horizontal field of view in degrees. * @param AspectRatio Width / Height. * @param NearPlane Near clip distance. * @param FarPlane Far clip distance. * @param ClipPlane World-space plane to clip against. * @param SurfaceTransform Transform of the surface (for converting clip plane to view space). * @return The oblique projection matrix. */ UFUNCTION(BlueprintCallable, BlueprintPure, Category = "Capture|CameraUtils") static FMatrix ComputeObliqueProjectionMatrix( float FOV, float AspectRatio, float NearPlane, float FarPlane, const FPlane& ClipPlane, const FTransform& SurfaceTransform); // ======================================================================== // Screen Coverage & Visibility // ======================================================================== /** * Estimate how much of the screen a capture surface occupies (0.0 to 1.0). * Uses the surface's bounding box corners projected to screen-space. * * @param SurfaceBounds Bounding box of the surface mesh in world space. * @param ViewerTransform World transform of the viewer's camera. * @param ViewerFOV Horizontal FOV of the viewer. * @param ScreenWidth Viewport width in pixels. * @param ScreenHeight Viewport height in pixels. * @return Estimated screen coverage ratio (0.0 to 1.0). */ UFUNCTION(BlueprintCallable, BlueprintPure, Category = "Capture|CameraUtils") static float ComputeScreenCoverage( const FBox& SurfaceBounds, const FTransform& ViewerTransform, float ViewerFOV, int32 ScreenWidth, int32 ScreenHeight); /** * Check whether the surface is visible to the viewer's frustum. * * @param SurfaceBounds Bounding box of the surface mesh in world space. * @param ViewerTransform World transform of the viewer's camera. * @param ViewerFOV Horizontal FOV. * @param ViewerAspectRatio Width / Height. * @param ViewerNearPlane Near clip distance. * @param ViewerFarPlane Far clip distance. * @return True if any part of the surface is within the frustum. */ UFUNCTION(BlueprintCallable, BlueprintPure, Category = "Capture|CameraUtils") static bool IsSurfaceVisibleToViewer( const FBox& SurfaceBounds, const FTransform& ViewerTransform, float ViewerFOV, float ViewerAspectRatio, float ViewerNearPlane, float ViewerFarPlane); // ======================================================================== // Quality Scoring // ======================================================================== /** * Compute a composite priority score for a capture surface. * Higher score = higher quality tier assignment. * Formula: (ScreenCoverage * 0.5) + (FacingAngle * 0.3) + (DistanceFactor * 0.1) + (ScriptedPriority * 0.1) * * @param ScreenCoverage How much screen real estate the surface occupies. * @param FacingAngle Dot product of viewer forward to surface normal. * @param DistanceToViewer Distance in world units. * @param MaxDistance Distance at which score drops to zero. * @param ScriptedPriority Priority override from gameplay systems (0.0 to 1.0). * @return Composite score (0.0 to 1.0). */ UFUNCTION(BlueprintCallable, BlueprintPure, Category = "Capture|CameraUtils") static float ComputeCompositeScore( float ScreenCoverage, float FacingAngle, float DistanceToViewer, float MaxDistance, float ScriptedPriority); };