浏览代码

Use a separate shape parameter for transmission

/RenderPassXR_Sandbox
Evgenii Golubev 7 年前
当前提交
f1785861
共有 6 个文件被更改,包括 70 次插入50 次删除
  1. 3
      Assets/ScriptableRenderPipeline/HDRenderPipeline/HDRenderPipeline.cs
  2. 4
      Assets/ScriptableRenderPipeline/HDRenderPipeline/Material/Lit/Lit.hlsl
  3. 11
      Assets/ScriptableRenderPipeline/HDRenderPipeline/Material/Lit/Resources/CombineSubsurfaceScattering.shader
  4. 94
      Assets/ScriptableRenderPipeline/HDRenderPipeline/Material/Lit/SubsurfaceScatteringProfile.cs
  5. 4
      Assets/ScriptableRenderPipeline/HDRenderPipeline/SceneSettings/Resources/DrawSssProfile.shader
  6. 4
      Assets/ScriptableRenderPipeline/HDRenderPipeline/SceneSettings/Resources/DrawTransmittanceGraph.shader

3
Assets/ScriptableRenderPipeline/HDRenderPipeline/HDRenderPipeline.cs


Shader.SetGlobalInt( "_TexturingModeFlags", (int)sssParameters.texturingModeFlags);
Shader.SetGlobalInt( "_TransmissionFlags", (int)sssParameters.transmissionFlags);
cmd.SetGlobalFloatArray( "_ThicknessRemaps", sssParameters.thicknessRemaps);
cmd.SetGlobalVectorArray("_ShapeParameters", sssParameters.shapeParameters);
cmd.SetGlobalVectorArray("_VolumeShapeParams", sssParameters.volumeShapeParams);
cmd.SetGlobalVectorArray("_VolumeAlbedos", sssParameters.volumeAlbedos);
renderContext.ExecuteCommandBuffer(cmd);

var cmd = new CommandBuffer() { name = "Subsurface Scattering" };
cmd.SetGlobalTexture("_IrradianceSource", m_CameraSubsurfaceBufferRT); // Cannot set a RT on a material
m_FilterAndCombineSubsurfaceScattering.SetVectorArray("_SurfaceShapeParams", sssParameters.surfaceShapeParams);
m_FilterAndCombineSubsurfaceScattering.SetFloatArray("_WorldScales", sssParameters.worldScales);
m_FilterAndCombineSubsurfaceScattering.SetFloatArray("_FilterKernelsNearField", sssParameters.filterKernelsNearField);
m_FilterAndCombineSubsurfaceScattering.SetFloatArray("_FilterKernelsFarField", sssParameters.filterKernelsFarField);

4
Assets/ScriptableRenderPipeline/HDRenderPipeline/Material/Lit/Lit.hlsl


uint _TexturingModeFlags; // 1 bit/profile; 0 = PreAndPostScatter, 1 = PostScatter
uint _TransmissionFlags; // 2 bit/profile; 0 = inf. thick, 1 = thin, 2 = regular
float _ThicknessRemaps[SSS_N_PROFILES][2]; // Remap: 0 = start, 1 = end - start
float4 _ShapeParameters[SSS_N_PROFILES]; // RGB = S = 1 / D; A = filter radius
float4 _VolumeShapeParams[SSS_N_PROFILES]; // RGB = S = 1 / D; A = unused
float4 _VolumeAlbedos[SSS_N_PROFILES]; // RGB = color, A = unused
//-----------------------------------------------------------------------------

if (bsdfData.enableTransmission)
{
bsdfData.transmittance = ComputeTransmittance(_ShapeParameters[subsurfaceProfile].rgb,
bsdfData.transmittance = ComputeTransmittance(_VolumeShapeParams[subsurfaceProfile].rgb,
_VolumeAlbedos[subsurfaceProfile].rgb,
bsdfData.thickness, bsdfData.subsurfaceRadius);
}

11
Assets/ScriptableRenderPipeline/HDRenderPipeline/Material/Lit/Resources/CombineSubsurfaceScattering.shader


// Inputs & outputs
//-------------------------------------------------------------------------------------
float _WorldScales[SSS_N_PROFILES]; // Size of the world unit in meters
float _FilterKernelsNearField[SSS_N_PROFILES][SSS_N_SAMPLES_NEAR_FIELD][2]; // 0 = radius, 1 = reciprocal of the PDF
float _FilterKernelsFarField[SSS_N_PROFILES][SSS_N_SAMPLES_FAR_FIELD][2]; // 0 = radius, 1 = reciprocal of the PDF
float4 _SurfaceShapeParams[SSS_N_PROFILES]; // RGB = S = 1 / D, A = filter radius
float _WorldScales[SSS_N_PROFILES]; // Size of the world unit in meters
float _FilterKernelsNearField[SSS_N_PROFILES][SSS_N_SAMPLES_NEAR_FIELD][2]; // 0 = radius, 1 = reciprocal of the PDF
float _FilterKernelsFarField[SSS_N_PROFILES][SSS_N_SAMPLES_FAR_FIELD][2]; // 0 = radius, 1 = reciprocal of the PDF
TEXTURE2D(_IrradianceSource); // Includes transmitted light
DECLARE_GBUFFER_TEXTURE(_GBufferTexture); // Contains the albedo and SSS parameters

int profileID = bsdfData.subsurfaceProfile;
float distScale = bsdfData.subsurfaceRadius;
float3 shapeParam = _ShapeParameters[profileID].rgb;
float maxDistance = _ShapeParameters[profileID].a;
float3 shapeParam = _SurfaceShapeParams[profileID].rgb;
float maxDistance = _SurfaceShapeParams[profileID].a;
// Reconstruct the view-space position.
float2 centerPosSS = posInput.positionSS;

94
Assets/ScriptableRenderPipeline/HDRenderPipeline/Material/Lit/SubsurfaceScatteringProfile.cs


[HideInInspector]
public int settingsIndex; // SubsurfaceScatteringSettings.profiles[i]
[SerializeField]
Vector3 m_S; // RGB = shape parameter: S = 1 / D
Vector3 m_SurfaceShapeParam; // RGB = shape parameter: S = 1 / D
[SerializeField]
Vector3 m_VolumeShapeParam; // RGB = shape parameter: S = 1 / D
[SerializeField]
float m_ScatteringDistance; // Filter radius (in millimeters)
[SerializeField]

m_FilterKernelFarField = new Vector2[SssConstants.SSS_N_SAMPLES_FAR_FIELD];
}
m_S = new Vector3();
m_SurfaceShapeParam = new Vector3();
m_S.x = FindFitForS(surfaceAlbedo.r);
m_S.y = FindFitForS(surfaceAlbedo.g);
m_S.z = FindFitForS(surfaceAlbedo.b);
m_SurfaceShapeParam.x = FindFitForS(surfaceAlbedo.r);
m_SurfaceShapeParam.y = FindFitForS(surfaceAlbedo.g);
m_SurfaceShapeParam.z = FindFitForS(surfaceAlbedo.b);
m_VolumeShapeParam.x = FindFitForS(volumeAlbedo.r);
m_VolumeShapeParam.y = FindFitForS(volumeAlbedo.g);
m_VolumeShapeParam.z = FindFitForS(volumeAlbedo.b);
m_S.x *= 1.0f / lenVolMeanFreePath;
m_S.y *= 1.0f / lenVolMeanFreePath;
m_S.z *= 1.0f / lenVolMeanFreePath;
m_SurfaceShapeParam *= 1.0f / lenVolMeanFreePath;
m_VolumeShapeParam *= 1.0f / lenVolMeanFreePath;
float s = Mathf.Min(m_S.x, m_S.y, m_S.z);
float s = Mathf.Min(m_SurfaceShapeParam.x, m_SurfaceShapeParam.y, m_SurfaceShapeParam.z);
// Importance sample the normalized diffusion profile for the computed value of 's'.
// ------------------------------------------------------------------------------------

}
}
public Vector3 shapeParameter
public Vector3 surfaceShapeParameter
{
// Set in BuildKernel().
get { return m_SurfaceShapeParam; }
}
public Vector3 volumeShapeParameter
get { return m_S; }
get { return m_VolumeShapeParam; }
}
public float scatteringDistance

[NonSerialized] public uint texturingModeFlags; // 1 bit/profile; 0 = PreAndPostScatter, 1 = PostScatter
[NonSerialized] public uint transmissionFlags; // 2 bit/profile; 0 = inf. thick, 1 = thin, 2 = regular
[NonSerialized] public float[] thicknessRemaps; // Remap: 0 = start, 1 = end - start
[NonSerialized] public Vector4[] shapeParameters; // RGB = S = 1 / D, A = filter radius
[NonSerialized] public Vector4[] surfaceShapeParams; // RGB = S = 1 / D, A = filter radius
[NonSerialized] public Vector4[] volumeShapeParams; // RGB = S = 1 / D, A = unused
[NonSerialized] public Vector4[] volumeAlbedos; // RGB = color, A = unused
[NonSerialized] public float[] worldScales; // Size of the world unit in meters
[NonSerialized] public float[] filterKernelsNearField; // 0 = radius, 1 = reciprocal of the PDF

texturingModeFlags = 0;
transmissionFlags = 0;
thicknessRemaps = null;
shapeParameters = null;
surfaceShapeParams = null;
volumeShapeParams = null;
filterKernelsNearField = null;
filterKernelsFarField = null;

thicknessRemaps = new float[thicknessRemapsLen];
}
const int worldScalesLen = SssConstants.SSS_N_PROFILES;
if (worldScales == null || worldScales.Length != worldScalesLen)
if (worldScales == null || worldScales.Length != SssConstants.SSS_N_PROFILES)
worldScales = new float[worldScalesLen];
worldScales = new float[SssConstants.SSS_N_PROFILES];
const int shapeParametersLen = SssConstants.SSS_N_PROFILES;
if (shapeParameters == null || shapeParameters.Length != shapeParametersLen)
if (surfaceShapeParams == null || surfaceShapeParams.Length != SssConstants.SSS_N_PROFILES)
shapeParameters = new Vector4[shapeParametersLen];
surfaceShapeParams = new Vector4[SssConstants.SSS_N_PROFILES];
}
if (volumeShapeParams == null || volumeShapeParams.Length != SssConstants.SSS_N_PROFILES)
{
volumeShapeParams = new Vector4[SssConstants.SSS_N_PROFILES];
const int volumeAlbedosLen = SssConstants.SSS_N_PROFILES;
if (volumeAlbedos == null || volumeAlbedos.Length != volumeAlbedosLen)
if (volumeAlbedos == null || volumeAlbedos.Length != SssConstants.SSS_N_PROFILES)
volumeAlbedos = new Vector4[volumeAlbedosLen];
volumeAlbedos = new Vector4[SssConstants.SSS_N_PROFILES];
}
const int filterKernelsNearFieldLen = 2 * SssConstants.SSS_N_PROFILES * SssConstants.SSS_N_SAMPLES_NEAR_FIELD;

thicknessRemaps[2 * i] = profiles[i].thicknessRemap.x;
thicknessRemaps[2 * i + 1] = profiles[i].thicknessRemap.y - profiles[i].thicknessRemap.x;
worldScales[i] = profiles[i].worldScale;
shapeParameters[i] = profiles[i].shapeParameter;
shapeParameters[i].w = profiles[i].scatteringDistance;
surfaceShapeParams[i] = profiles[i].surfaceShapeParameter;
surfaceShapeParams[i].w = profiles[i].scatteringDistance;
volumeShapeParams[i] = profiles[i].volumeShapeParameter;
volumeAlbedos[i] = profiles[i].volumeAlbedo;
for (int j = 0, n = SssConstants.SSS_N_SAMPLES_NEAR_FIELD; j < n; j++)

{
int i = SssConstants.SSS_NEUTRAL_PROFILE_ID;
shapeParameters[i] = Vector4.zero;
volumeAlbedos[i] = Vector4.zero;
worldScales[i] = 1.0f;
surfaceShapeParams[i] = Vector4.zero;
volumeShapeParams[i] = Vector4.zero;
volumeAlbedos[i] = Vector4.zero;
worldScales[i] = 1.0f;
for (int j = 0, n = SssConstants.SSS_N_SAMPLES_NEAR_FIELD; j < n; j++)
{

private RenderTexture m_ProfileImage, m_TransmittanceImage;
private Material m_ProfileMaterial, m_TransmittanceMaterial;
private SerializedProperty m_LenVolMeanFreePath, m_ScatteringDistance, m_SurfaceAlbedo, m_VolumeAlbedo, m_S,
private SerializedProperty m_LenVolMeanFreePath, m_ScatteringDistance, m_SurfaceAlbedo, m_VolumeAlbedo, m_SurfaceShapeParam, m_VolumeShapeParam,
m_TexturingMode, m_TransmissionMode, m_ThicknessRemap, m_WorldScale;
void OnEnable()

m_LenVolMeanFreePath = serializedObject.FindProperty("lenVolMeanFreePath");
m_ScatteringDistance = serializedObject.FindProperty("m_ScatteringDistance");
m_S = serializedObject.FindProperty("m_S");
m_SurfaceShapeParam = serializedObject.FindProperty("m_SurfaceShapeParam");
m_VolumeShapeParam = serializedObject.FindProperty("m_VolumeShapeParam");
m_TexturingMode = serializedObject.FindProperty("texturingMode");
m_TransmissionMode = serializedObject.FindProperty("transmissionMode");
m_ThicknessRemap = serializedObject.FindProperty("thicknessRemap");

EditorGUILayout.Space();
}
float d = m_ScatteringDistance.floatValue;
Vector4 A = m_SurfaceAlbedo.colorValue;
Vector4 V = m_VolumeAlbedo.colorValue;
Vector3 S = m_S.vector3Value;
Vector2 R = m_ThicknessRemap.vector2Value;
float d = m_ScatteringDistance.floatValue;
Vector4 aS = m_SurfaceAlbedo.colorValue;
Vector4 aV = m_VolumeAlbedo.colorValue;
Vector3 sS = m_SurfaceShapeParam.vector3Value;
Vector3 sV = m_VolumeShapeParam.vector3Value;
Vector2 R = m_ThicknessRemap.vector2Value;
m_ProfileMaterial.SetVector("_SurfaceAlbedo", A);
m_ProfileMaterial.SetVector("_ShapeParameter", S);
m_ProfileMaterial.SetVector("_SurfaceAlbedo", aS);
m_ProfileMaterial.SetVector("_SurfaceShapeParam", sS);
EditorGUI.DrawPreviewTexture(GUILayoutUtility.GetRect(256, 256), m_ProfileImage, m_ProfileMaterial, ScaleMode.ScaleToFit, 1.0f);
EditorGUILayout.Space();

// Draw the transmittance graph.
m_TransmittanceMaterial.SetFloat("_ScatteringDistance", d);
m_TransmittanceMaterial.SetVector("_VolumeAlbedo", transmissionEnabled ? V : Vector4.zero);
m_TransmittanceMaterial.SetVector("_ShapeParameter", S);
m_TransmittanceMaterial.SetVector("_VolumeAlbedo", transmissionEnabled ? aV : Vector4.zero);
m_TransmittanceMaterial.SetVector("_VolumeShapeParam", sV);
m_TransmittanceMaterial.SetVector("_ThicknessRemap", R);
EditorGUI.DrawPreviewTexture(GUILayoutUtility.GetRect(16, 16), m_TransmittanceImage, m_TransmittanceMaterial, ScaleMode.ScaleToFit, 16.0f);

4
Assets/ScriptableRenderPipeline/HDRenderPipeline/SceneSettings/Resources/DrawSssProfile.shader


// Inputs & outputs
//-------------------------------------------------------------------------------------
float4 _SurfaceAlbedo, _ShapeParameter;
float4 _SurfaceAlbedo, _SurfaceShapeParam;
float _ScatteringDistance; // See 'SubsurfaceScatteringProfile'
//-------------------------------------------------------------------------------------

float4 Frag(Varyings input) : SV_Target
{
float r = (2 * length(input.texcoord - 0.5)) * _ScatteringDistance;
float3 S = _ShapeParameter.rgb;
float3 S = _SurfaceShapeParam.rgb;
float3 M = S * (exp(-r * S) + exp(-r * S * (1.0 / 3.0))) / (8 * PI * r);
// N.b.: we multiply by the surface albedo of the actual geometry during shading.

4
Assets/ScriptableRenderPipeline/HDRenderPipeline/SceneSettings/Resources/DrawTransmittanceGraph.shader


// Inputs & outputs
//-------------------------------------------------------------------------------------
float4 _VolumeAlbedo, _ShapeParameter, _ThicknessRemap;
float4 _VolumeAlbedo, _VolumeShapeParam, _ThicknessRemap;
float _ScatteringDistance; // See 'SubsurfaceScatteringProfile'
//-------------------------------------------------------------------------------------

float4 Frag(Varyings input) : SV_Target
{
float d = (_ThicknessRemap.x + input.texcoord.x * (_ThicknessRemap.y - _ThicknessRemap.x));
float3 T = ComputeTransmittance(_ShapeParameter.rgb, float3(1, 1, 1), d, 1);
float3 T = ComputeTransmittance(_VolumeShapeParam.rgb, float3(1, 1, 1), d, 1);
// Apply gamma for visualization only. Do not apply gamma to the color.
return float4(pow(T, 1.0 / 3) * _VolumeAlbedo.rgb, 1);

正在加载...
取消
保存