namespace Sandbox.Rendering; /// /// When manually rendering a camera this will let you override specific /// elements of that render. This means you can use most of the camera's /// properties, but override some without disturbing the camera itself. /// public struct ViewSetup { /// /// Overrides the camera's position and rotation /// public Transform? Transform; /// /// Overrides the camera's field of view /// public float? FieldOfView; /// /// Overrides the camera's znear /// public float? ZNear; /// /// Overrides the camera's zfar /// public float? ZFar; /// /// Overrides the camera's clear color /// public Color? ClearColor; /// /// Overrides the camera's projection matrix /// public Matrix? ProjectionMatrix; /// /// Allows overriding gradient fog for this view /// public GradientFogSetup? GradientFog; /// /// If set then the regular scene's ambient light will be multiplied by this /// public Color? AmbientLightTint; /// /// If set then this will be added to the ambient light color /// public Color? AmbientLightAdd; /// /// Clipspace is usually used for rendering posters, or center-offsetting the view. You're basically zooming /// into a subrect of the clipspace. So imagine you draw a smaller rect inside the first rect of the frustum.. /// that's what you're gonna render - that rect. /// public Vector4? ClipSpaceBounds; /// /// When rendering to a texture, this allows you to flip the view horizontally. /// public bool? FlipX; /// /// When rendering to a texture, this allows you to flip the view vertically. /// public bool? FlipY; /// /// Whether post processing should be enabled for this view. If null it will use the camera's setting. /// public bool? EnablePostprocessing; /// /// If you're rendering a subview this will allow the renderer to find the same view again next frame /// public int ViewHash; } /// /// Setup for defining gradient fog in a view /// public struct GradientFogSetup { /// /// Whether the fog is enabled. /// public bool Enabled { get; set; } /// /// Start distance of the fog. /// public float StartDistance { get; set; } /// /// End distance of the fog. /// public float EndDistance { get; set; } /// /// The starting height of the gradient fog. /// public float StartHeight { get; set; } /// /// The ending height of the gradient fog. /// public float EndHeight { get; set; } /// /// The maximum opacity of the gradient fog. /// public float MaximumOpacity { get; set; } /// /// The color of the gradient fog. /// public Color Color { get; set; } /// /// The exponent controlling the distance-based falloff of the fog. /// public float DistanceFalloffExponent { get; set; } /// /// The exponent controlling the vertical falloff of the fog. /// public float VerticalFalloffExponent { get; set; } internal void Apply( RenderAttributes attributes ) { if ( !Enabled ) { attributes.SetCombo( "D_ENABLE_GRADIENT_FOG", 0 ); return; } attributes.SetCombo( "D_ENABLE_GRADIENT_FOG", 1 ); attributes.Set( "GradientFogParams", new Vector4( StartDistance, EndDistance, StartHeight, EndHeight ) ); attributes.Set( "GradientFogParams2", new Vector4( MaximumOpacity, DistanceFalloffExponent, VerticalFalloffExponent, 0.0f ) ); attributes.Set( "GradientFogParams3", new Vector4( Color, 0.0f ) * Color.a ); } /// /// Lerp this GradientFogSetup to a another, allowing transition states. /// public GradientFogSetup LerpTo( GradientFogSetup desired, float delta, bool clamp = true ) { if ( Enabled != desired.Enabled ) return desired; GradientFogSetup newState = default; newState.StartDistance = StartDistance.LerpTo( desired.StartDistance, delta, clamp ); newState.EndDistance = EndDistance.LerpTo( desired.EndDistance, delta, clamp ); newState.StartHeight = StartHeight.LerpTo( desired.StartHeight, delta, clamp ); newState.EndHeight = EndHeight.LerpTo( desired.EndHeight, delta, clamp ); newState.MaximumOpacity = MaximumOpacity.LerpTo( desired.MaximumOpacity, delta, clamp ); newState.DistanceFalloffExponent = DistanceFalloffExponent.LerpTo( desired.DistanceFalloffExponent, delta, clamp ); newState.VerticalFalloffExponent = VerticalFalloffExponent.LerpTo( desired.VerticalFalloffExponent, delta, clamp ); newState.Color = Color.Lerp( Color, desired.Color, delta ); return newState; } } /// /// Allows special setup for reflections, such as offsetting the reflection plane /// public struct ReflectionSetup { /// /// Allows overriding everything you normally can /// public ViewSetup ViewSetup; /// /// Offset the reflection plane's clip plane by this much /// public float ClipOffset; /// /// If true we'll render the reflection even if we're behind the plane /// public bool RenderBehind; /// /// If we can't render the reflection and this is set, we'll clear the render target to this color /// public Color? FallbackColor { get; set; } // TODO - stencil? clip rect? } /// /// Allows special setup for refraction, such as offsetting the clip plane /// public struct RefractionSetup { /// /// Allows overriding everything you normally can /// public ViewSetup ViewSetup; /// /// Offset the reflection plane's clip plane by this much /// public float ClipOffset; /// /// If true we'll render the reflection even if we're behind the plane /// public bool RenderBehind; /// /// If we can't render the reflection and this is set, we'll clear the render target to this color /// public Color? FallbackColor { get; set; } // TODO - stencil? clip rect? } /// /// When manually rendering a Renderer this will let you override specific /// elements of that render. This means you can use most of the Renderer's /// properties, but override some without disturbing the Renderer itself. /// public struct RendererSetup { /// /// Overrides the transform used for rendering /// public Transform? Transform; /// /// Overrides the color used for rendering /// public Color? Color; /// /// Overrides the material used for rendering /// public Material Material; }