浏览代码

Refactor things again to [GenerateHLSL]

/main
Evgenii Golubev 7 年前
当前提交
b4da729b
共有 4 个文件被更改,包括 186 次插入134 次删除
  1. 270
      ScriptableRenderPipeline/Core/CoreRP/GeometryUtils.cs
  2. 3
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Lighting/Volumetrics/VolumetricLighting.cs
  3. 38
      ScriptableRenderPipeline/Core/CoreRP/GeometryUtils.cs.hlsl
  4. 9
      ScriptableRenderPipeline/Core/CoreRP/GeometryUtils.cs.hlsl.meta

270
ScriptableRenderPipeline/Core/CoreRP/GeometryUtils.cs


namespace UnityEngine.Experimental.Rendering
{
public static class GeometryUtils
{
public static readonly Matrix4x4 FlipMatrixLHSRHS = Matrix4x4.Scale(new Vector3(1, 1, -1));
public static Vector4 Plane(Vector3 position, Vector3 normal)
{
var n = normal;
var d = -Vector3.Dot(n, position);
var plane = new Vector4(n.x, n.y, n.z, d);
return plane;
}
public static Vector4 CameraSpacePlane(Matrix4x4 worldToCamera, Vector3 pos, Vector3 normal, float sideSign = 1, float clipPlaneOffset = 0)
{
var offsetPos = pos + normal * clipPlaneOffset;
var cpos = worldToCamera.MultiplyPoint(offsetPos);
var cnormal = worldToCamera.MultiplyVector(normal).normalized * sideSign;
return new Vector4(cnormal.x, cnormal.y, cnormal.z, -Vector3.Dot(cpos, cnormal));
}
public static Matrix4x4 CalculateWorldToCameraMatrixRHS(Vector3 position, Quaternion rotation)
{
return Matrix4x4.Scale(new Vector3(1, 1, -1)) * Matrix4x4.TRS(position, rotation, Vector3.one).inverse;
}
public static Matrix4x4 CalculateWorldToCameraMatrixRHS(Transform transform)
{
return Matrix4x4.Scale(new Vector3(1, 1, -1)) * transform.localToWorldMatrix.inverse;
}
public static Matrix4x4 CalculateObliqueMatrix(Matrix4x4 sourceProjection, Vector4 clipPlane)
{
var projection = sourceProjection;
var inversion = sourceProjection.inverse;
var cps = new Vector4(
Mathf.Sign(clipPlane.x),
Mathf.Sign(clipPlane.y),
1.0f,
1.0f);
var q = inversion * cps;
var c = clipPlane * (2.0f / Vector4.Dot(clipPlane, q));
projection[2] = c.x - projection[3];
projection[6] = c.y - projection[7];
projection[10] = c.z - projection[11];
projection[14] = c.w - projection[15];
return projection;
}
public static Matrix4x4 CalculateReflectionMatrix(Vector3 position, Vector3 normal)
{
return CalculateReflectionMatrix(Plane(position, normal.normalized));
}
public static Matrix4x4 CalculateReflectionMatrix(Vector4 plane)
{
var reflectionMat = new Matrix4x4();
reflectionMat.m00 = (1F - 2F * plane[0] * plane[0]);
reflectionMat.m01 = (-2F * plane[0] * plane[1]);
reflectionMat.m02 = (-2F * plane[0] * plane[2]);
reflectionMat.m03 = (-2F * plane[3] * plane[0]);
reflectionMat.m10 = (-2F * plane[1] * plane[0]);
reflectionMat.m11 = (1F - 2F * plane[1] * plane[1]);
reflectionMat.m12 = (-2F * plane[1] * plane[2]);
reflectionMat.m13 = (-2F * plane[3] * plane[1]);
reflectionMat.m20 = (-2F * plane[2] * plane[0]);
reflectionMat.m21 = (-2F * plane[2] * plane[1]);
reflectionMat.m22 = (1F - 2F * plane[2] * plane[2]);
reflectionMat.m23 = (-2F * plane[3] * plane[2]);
reflectionMat.m30 = 0F;
reflectionMat.m31 = 0F;
reflectionMat.m32 = 0F;
reflectionMat.m33 = 1F;
return reflectionMat;
}
public static Matrix4x4 GetWorldToCameraMatrixLHS(this Camera camera)
{
return FlipMatrixLHSRHS * camera.worldToCameraMatrix;
}
public static Matrix4x4 GetProjectionMatrixLHS(this Camera camera)
{
return camera.projectionMatrix * FlipMatrixLHSRHS;
}
public static Matrix4x4 CalculateProjectionMatrix(Camera camera)
{
if (camera.orthographic)
{
var h = camera.orthographicSize;
var w = camera.orthographicSize * camera.aspect;
return Matrix4x4.Ortho(-w, w, -h, h, camera.nearClipPlane, camera.farClipPlane);
}
else
return Matrix4x4.Perspective(camera.fieldOfView, camera.aspect, camera.nearClipPlane, camera.farClipPlane);
}
}
public struct Frustum
{
public Plane[] planes; // Left, right, top, bottom, near, far

GeometryUtility.CalculateFrustumPlanes(viewProjMatrix, frustum.planes);
float nd = -1.0f;
nd = 0.0f;
// See "Fast Extraction of Viewing Frustum Planes" by Gribb and Hartmann.
Vector3 f = new Vector3(viewProjMatrix.m20, viewProjMatrix.m21, viewProjMatrix.m22);
float s = (float)(1.0 / Math.Sqrt(f.sqrMagnitude));

frustum.corners[1] = invViewProjMatrix.MultiplyPoint(new Vector3( 1, -1, 1));
frustum.corners[2] = invViewProjMatrix.MultiplyPoint(new Vector3(-1, 1, 1));
frustum.corners[3] = invViewProjMatrix.MultiplyPoint(new Vector3( 1, 1, 1));
frustum.corners[4] = invViewProjMatrix.MultiplyPoint(new Vector3(-1, -1, 0));
frustum.corners[5] = invViewProjMatrix.MultiplyPoint(new Vector3( 1, -1, 0));
frustum.corners[6] = invViewProjMatrix.MultiplyPoint(new Vector3(-1, 1, 0));
frustum.corners[7] = invViewProjMatrix.MultiplyPoint(new Vector3( 1, 1, 0));
frustum.corners[4] = invViewProjMatrix.MultiplyPoint(new Vector3(-1, -1, nd));
frustum.corners[5] = invViewProjMatrix.MultiplyPoint(new Vector3( 1, -1, nd));
frustum.corners[6] = invViewProjMatrix.MultiplyPoint(new Vector3(-1, 1, nd));
frustum.corners[7] = invViewProjMatrix.MultiplyPoint(new Vector3( 1, 1, nd));
}
} // struct Frustum
[GenerateHLSL]
// TODO: in the shader, merge axes and extents, and 16-byte align the data structure.
public Vector3 center;
public Vector3 right, up, forward; // X, Y, Z, normalized
public Vector3 extents; // Size of the half-diagonal
public Vector4 center; // w is unused
public Vector4 right, up, forward; // {x, y, z} = normalized local axis, w = 1/2 * size along the axis
obb.center = t.position;
obb.right = t.right;
obb.up = t.up;
obb.forward = t.forward;
obb.extents = t.localScale * 0.5f;
obb.center = t.position;
obb.right = t.right;
obb.right.w = 0.5f * t.localScale.x;
obb.up = t.up;
obb.up.w = 0.5f * t.localScale.y;
obb.forward = t.forward;
obb.forward.w = 0.5f * t.localScale.z;
} // struct OrientedBBox
public static class GeometryUtils
{
public bool OverlapsFrustum(Frustum frustum, int numPlanes, int numCorners, Vector3 cameraRelativeOffset)
public static bool Overlap(OrientedBBox obb, Vector3 cameraRelativeOffset,
Frustum frustum, int numPlanes, int numCorners)
Vector3 relCenter = center + cameraRelativeOffset;
Vector3 relCenter = (Vector3)obb.center + cameraRelativeOffset;
bool overlap = true;

float d = frustum.planes[i].distance;
// Max projection of the half-diagonal onto the normal (always positive).
float maxHalfDiagProj = extents.x * Mathf.Abs(Vector3.Dot(n, right))
+ extents.y * Mathf.Abs(Vector3.Dot(n, up))
+ extents.z * Mathf.Abs(Vector3.Dot(n, forward));
float maxHalfDiagProj = Mathf.Abs(Vector3.Dot(n, obb.right)) * obb.right.w
+ Mathf.Abs(Vector3.Dot(n, obb.up)) * obb.up.w
+ Mathf.Abs(Vector3.Dot(n, obb.forward)) * obb.forward.w;
// Negative distance -> center behind the plane (outside).
float centerToPlaneDist = Vector3.Dot(n, relCenter) + d;

// We can exploit the symmetry of the box by only testing against 3 planes rather than 6.
Plane[] planes = new Plane[3];
planes[0].normal = right;
planes[0].distance = extents.x;
planes[1].normal = up;
planes[1].distance = extents.y;
planes[2].normal = forward;
planes[2].distance = extents.z;
planes[0].normal = obb.right;
planes[0].distance = obb.right.w;
planes[1].normal = obb.up;
planes[1].distance = obb.up.w;
planes[2].normal = obb.forward;
planes[2].distance = obb.forward.w;
for (int i = 0; overlap && i < 3; i++)
{

return overlap;
}
} // struct OrientedBBox
public static readonly Matrix4x4 FlipMatrixLHSRHS = Matrix4x4.Scale(new Vector3(1, 1, -1));
public static Vector4 Plane(Vector3 position, Vector3 normal)
{
var n = normal;
var d = -Vector3.Dot(n, position);
var plane = new Vector4(n.x, n.y, n.z, d);
return plane;
}
public static Vector4 CameraSpacePlane(Matrix4x4 worldToCamera, Vector3 pos, Vector3 normal, float sideSign = 1, float clipPlaneOffset = 0)
{
var offsetPos = pos + normal * clipPlaneOffset;
var cpos = worldToCamera.MultiplyPoint(offsetPos);
var cnormal = worldToCamera.MultiplyVector(normal).normalized * sideSign;
return new Vector4(cnormal.x, cnormal.y, cnormal.z, -Vector3.Dot(cpos, cnormal));
}
public static Matrix4x4 CalculateWorldToCameraMatrixRHS(Vector3 position, Quaternion rotation)
{
return Matrix4x4.Scale(new Vector3(1, 1, -1)) * Matrix4x4.TRS(position, rotation, Vector3.one).inverse;
}
public static Matrix4x4 CalculateWorldToCameraMatrixRHS(Transform transform)
{
return Matrix4x4.Scale(new Vector3(1, 1, -1)) * transform.localToWorldMatrix.inverse;
}
public static Matrix4x4 CalculateObliqueMatrix(Matrix4x4 sourceProjection, Vector4 clipPlane)
{
var projection = sourceProjection;
var inversion = sourceProjection.inverse;
var cps = new Vector4(
Mathf.Sign(clipPlane.x),
Mathf.Sign(clipPlane.y),
1.0f,
1.0f);
var q = inversion * cps;
var c = clipPlane * (2.0f / Vector4.Dot(clipPlane, q));
projection[2] = c.x - projection[3];
projection[6] = c.y - projection[7];
projection[10] = c.z - projection[11];
projection[14] = c.w - projection[15];
return projection;
}
public static Matrix4x4 CalculateReflectionMatrix(Vector3 position, Vector3 normal)
{
return CalculateReflectionMatrix(Plane(position, normal.normalized));
}
public static Matrix4x4 CalculateReflectionMatrix(Vector4 plane)
{
var reflectionMat = new Matrix4x4();
reflectionMat.m00 = (1F - 2F * plane[0] * plane[0]);
reflectionMat.m01 = (-2F * plane[0] * plane[1]);
reflectionMat.m02 = (-2F * plane[0] * plane[2]);
reflectionMat.m03 = (-2F * plane[3] * plane[0]);
reflectionMat.m10 = (-2F * plane[1] * plane[0]);
reflectionMat.m11 = (1F - 2F * plane[1] * plane[1]);
reflectionMat.m12 = (-2F * plane[1] * plane[2]);
reflectionMat.m13 = (-2F * plane[3] * plane[1]);
reflectionMat.m20 = (-2F * plane[2] * plane[0]);
reflectionMat.m21 = (-2F * plane[2] * plane[1]);
reflectionMat.m22 = (1F - 2F * plane[2] * plane[2]);
reflectionMat.m23 = (-2F * plane[3] * plane[2]);
reflectionMat.m30 = 0F;
reflectionMat.m31 = 0F;
reflectionMat.m32 = 0F;
reflectionMat.m33 = 1F;
return reflectionMat;
}
public static Matrix4x4 GetWorldToCameraMatrixLHS(this Camera camera)
{
return FlipMatrixLHSRHS * camera.worldToCameraMatrix;
}
public static Matrix4x4 GetProjectionMatrixLHS(this Camera camera)
{
return camera.projectionMatrix * FlipMatrixLHSRHS;
}
public static Matrix4x4 CalculateProjectionMatrix(Camera camera)
{
if (camera.orthographic)
{
var h = camera.orthographicSize;
var w = camera.orthographicSize * camera.aspect;
return Matrix4x4.Ortho(-w, w, -h, h, camera.nearClipPlane, camera.farClipPlane);
}
else
return Matrix4x4.Perspective(camera.fieldOfView, camera.aspect, camera.nearClipPlane, camera.farClipPlane);
}
} // class GeometryUtils
}

3
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Lighting/Volumetrics/VolumetricLighting.cs


public void VoxelizeDensityVolumes(HDCamera camera, CommandBuffer cmd)
{
if (preset == VolumetricLightingPreset.Off) return;
if (camera.camera.cameraType != CameraType.SceneView) return;
Vector3 camPosition = camera.camera.transform.position;
Vector3 camOffset = Vector3.zero; // World-origin-relative

var obb = OrientedBBox.Create(fogComponent.transform);
// Frustum cull on the CPU for now. TODO: do it on the GPU.
if (!obb.OverlapsFrustum(camera.frustum, 6, 8, camOffset))
if (!GeometryUtils.Overlap(obb, camOffset, camera.frustum, 6, 8))
{
Debug.Log("Culled.");
}

38
ScriptableRenderPipeline/Core/CoreRP/GeometryUtils.cs.hlsl


//
// This file was automatically generated. Please don't edit by hand.
//
#ifndef GEOMETRYUTILS_CS_HLSL
#define GEOMETRYUTILS_CS_HLSL
// Generated from UnityEngine.Experimental.Rendering.OrientedBBox
// PackingRules = Exact
struct OrientedBBox
{
float4 center;
float4 right;
float4 up;
float4 forward;
};
//
// Accessors for UnityEngine.Experimental.Rendering.OrientedBBox
//
float4 GetCenter(OrientedBBox value)
{
return value.center;
}
float4 GetRight(OrientedBBox value)
{
return value.right;
}
float4 GetUp(OrientedBBox value)
{
return value.up;
}
float4 GetForward(OrientedBBox value)
{
return value.forward;
}
#endif

9
ScriptableRenderPipeline/Core/CoreRP/GeometryUtils.cs.hlsl.meta


fileFormatVersion: 2
guid: c168c5bb5d2fae84499b8ee8f2a3cdbc
ShaderImporter:
externalObjects: {}
defaultTextures: []
nonModifiableTextures: []
userData:
assetBundleName:
assetBundleVariant:
正在加载...
取消
保存