From 6579d30f558908c23889f9e691a5932a49ecdedd Mon Sep 17 00:00:00 2001 From: yum Date: Sat, 29 Mar 2025 20:23:19 -0700 Subject: Optimize tessellation code - vectorizing and frustrum culling --- shatter_wave.cginc | 39 ++++++++++++++++++++++++--------------- 1 file changed, 24 insertions(+), 15 deletions(-) (limited to 'shatter_wave.cginc') diff --git a/shatter_wave.cginc b/shatter_wave.cginc index 8636df6..f86a6ac 100644 --- a/shatter_wave.cginc +++ b/shatter_wave.cginc @@ -15,11 +15,22 @@ void shatterWaveVert(inout float3 objPos, float3 objNormal, float3 objTangent) { float3 wave_axis2 = normalize(_Shatter_Wave_Direction2); float3 wave_axis3 = normalize(_Shatter_Wave_Direction3); float4x3 wave_axes = float4x3(wave_axis0, wave_axis1, wave_axis2, wave_axis3); - float4x3 objPos_proj; - objPos_proj[0] = dot(objPos, wave_axis0) * normalize(wave_axis0); - objPos_proj[1] = dot(objPos, wave_axis1) * normalize(wave_axis1); - objPos_proj[2] = dot(objPos, wave_axis2) * normalize(wave_axis2); - objPos_proj[3] = dot(objPos, wave_axis3) * normalize(wave_axis3); + + float4 projDots = mul(wave_axes, objPos); + // Equivalent code: + // float4 projDots = float4( + // dot(objPos, wave_axis0), + // dot(objPos, wave_axis1), + // dot(objPos, wave_axis2), + // dot(objPos, wave_axis3) + // ); + + float4x3 objPos_proj = float4x3( + projDots.x * wave_axis0, + projDots.y * wave_axis1, + projDots.z * wave_axis2, + projDots.w * wave_axis3 + ); #if defined(_SHATTER_WAVE_AUDIOLINK) float4 wave_t; @@ -64,25 +75,23 @@ void shatterWaveVert(inout float3 objPos, float3 objNormal, float3 objTangent) { float4 wave_center = wave_t; - // TODO calculate signed distance from wave center - float4 distance_signed; - for (uint i = 0; i < 4; i++) { - float3 dist_to_center = objPos_proj[i] - wave_center[i] * wave_axes[i]; - distance_signed[i] = dot(dist_to_center, wave_axes[i]); - } + float4 distance_signed = float4( + dot(objPos_proj[0] - wave_center.x * wave_axes[0], wave_axes[0]), + dot(objPos_proj[1] - wave_center.y * wave_axes[1], wave_axes[1]), + dot(objPos_proj[2] - wave_center.z * wave_axes[2], wave_axes[2]), + dot(objPos_proj[3] - wave_center.w * wave_axes[3], wave_axes[3]) + ); #if defined(_SHATTER_WAVE_ROTATION) float4 thetas = clamp(distance_signed * _Shatter_Wave_Rotation_Strength, -1, 1) * TAU; + [unroll] for (uint i = 0; i < 4; i++) { objPos = rotate_vector(objPos, get_quaternion(wave_axes[i], thetas[i])); } #endif float4 offset = exp(-abs(distance_signed) * _Shatter_Wave_Power) * _Shatter_Wave_Amplitude; - objPos += objNormal * offset[0]; - objPos += objNormal * offset[1]; - objPos += objNormal * offset[2]; - objPos += objNormal * offset[3]; + objPos += objNormal * (offset.x + offset.y + offset.z + offset.w); } void shatterWaveFrag(inout float3 normal, float3 objPos) { -- cgit v1.2.3