浏览代码

Merge pull request #944 from Unity-Technologies/support-iridescence

Add support for Iridescence in Lit
/main
GitHub 7 年前
当前提交
f618fcd9
共有 13 个文件被更改,包括 375 次插入65 次删除
  1. 76
      SampleScenes/HDTest/GraphicTest/SSS/head.OBJ.meta
  2. 8
      ScriptableRenderPipeline/Core/CoreRP/ShaderLibrary/BSDF.hlsl
  3. 12
      ScriptableRenderPipeline/Core/CoreRP/ShaderLibrary/CommonMaterial.hlsl
  4. 62
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Editor/Material/Lit/LitUI.cs
  5. 3
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/LayeredLit/LayeredLitData.hlsl
  6. 8
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.cs
  7. 42
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.cs.hlsl
  8. 173
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.hlsl
  9. 9
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.shader
  10. 22
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/LitDataIndividualLayer.hlsl
  11. 13
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/LitProperties.hlsl
  12. 10
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/LitTessellation.shader
  13. 2
      ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Material.hlsl

76
SampleScenes/HDTest/GraphicTest/SSS/head.OBJ.meta


fileFormatVersion: 2
guid: c567c8ceaf4b2a640926180289847290
timeCreated: 1494507413
licenseType: Pro
serializedVersion: 21
serializedVersion: 22
fileIDToRecycleName:
100000: Group12
100002: Group14

4300020: Group4
4300022: Group5
4300024: Group7
2186277476908879412: ImportLogs
externalObjects:
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group12Mat
second: {fileID: 2100000, guid: 30f21721af7ebd0448be0dcfec0074f1, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group14Mat
second: {fileID: 2100000, guid: 2ee351eaf894bd84ea7b01943fbe0563, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group19Mat
second: {fileID: 2100000, guid: 3cebc5e48633f5945902c68cf16bf096, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group24Mat
second: {fileID: 2100000, guid: 3c9dc1f55aa963c44b6666d154356723, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group26Mat
second: {fileID: 2100000, guid: 50b1d4b20bf986149bc42528026f4305, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group28Mat
second: {fileID: 2100000, guid: 91dd7c7f3843b724fa99ff46c33ffd03, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group2Mat
second: {fileID: 2100000, guid: 1dba3e60230b9724eb0cc8bb6aed491a, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group33Mat
second: {fileID: 2100000, guid: 28d8c86f3603f79489848d863b9cbee0, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group35Mat
second: {fileID: 2100000, guid: bf6c40b91880c51499ed7632da19afec, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group39Mat
second: {fileID: 2100000, guid: e7b64b2987ce9d44d924bc4a614cce75, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group4Mat
second: {fileID: 2100000, guid: 3eb5f7c7baae8484cb76fd9dcd65709c, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group5Mat
second: {fileID: 2100000, guid: ab0ed2eee715f5a40899e5948c2f78bd, type: 2}
- first:
type: UnityEngine:Material
assembly: UnityEngine.CoreModule
name: Group7Mat
second: {fileID: 2100000, guid: b76a948b681a8ec488d8ccdcc4173f4c, type: 2}
materialLocation: 0
animations:
legacyGenerateAnimations: 4
bakeSimulation: 0

animationImportWarnings:
animationRetargetingWarnings:
animationDoRetargetingWarnings: 0
importAnimatedCustomProperties: 0
importConstraints: 0
animationCompression: 1
animationRotationError: 0.5
animationPositionError: 0.5

optimizeMeshForGPU: 1
keepQuads: 0
weldVertices: 1
preserveHierarchy: 0
indexFormat: 1
secondaryUVAngleDistortion: 8
secondaryUVAreaDistortion: 15.000001
secondaryUVHardAngle: 88

8
ScriptableRenderPipeline/Core/CoreRP/ShaderLibrary/BSDF.hlsl


return F_Transm_Schlick(f0, 1.0, u); // sub mul mul mad mad*3
}
// Ref: https://seblagarde.wordpress.com/2013/04/29/memo-on-fresnel-equations/
// Fresnel dieletric / dielectric
real F_Fresnel(real ior, real u)
{
float g = sqrt(Sq(ior) + Sq(u) - 1.0);
return 0.5 * Sq((g - u) / (g + u)) * (1.0 + Sq(((g + u) * u - 1.0) / ((g - u) * u + 1.0)));
}
//-----------------------------------------------------------------------------
// Specular BRDF
//-----------------------------------------------------------------------------

12
ScriptableRenderPipeline/Core/CoreRP/ShaderLibrary/CommonMaterial.hlsl


// Note: making the constant too small results in aliasing.
real ClampRoughnessForAnalyticalLights(real roughness)
{
return max(roughness, 1.0/1024.0);
return max(roughness, 1.0 / 1024.0);
}
void ConvertAnisotropyToRoughness(real perceptualRoughness, real anisotropy, out real roughnessT, out real roughnessB)

// ior is a value between 1.0 and 2.5
// Assume air interface for top
real IORToFresnel0(real ior)
real IorToFresnel0(real ior)
real IORToFresnel0(real baseIor, real topIor)
real IorToFresnel0(real baseIor, real topIor)
{
return Sq((baseIor - topIor) / (baseIor + topIor));
}

real Fresnel0ToIOR(real fresnel0)
real Fresnel0ToIor(real fresnel0)
{
real sqrtF0 = sqrt(fresnel0);
return (1.0 + sqrtF0) / (1.0 - sqrtF0);

// This function is equivalent to IORToFresnel0(Fresnel0ToIOR(fresnel0), 1.5)
// This function is equivalent to IorToFresnel0(Fresnel0ToIor(fresnel0), 1.5)
// mean
// real sqrtF0 = sqrt(fresnel0);
// return Sq(1.0 - 5.0 * sqrtF0) / Sq(5.0 - sqrtF0);

// Determine the blend weights for the 3 planar projections.
real3 blendWeights = abs(normal);
// Tighten up the blending zone
blendWeights = (blendWeights - 0.2) * 7.0;
blendWeights = (blendWeights - 0.2);
blendWeights = blendWeights * blendWeights * blendWeights; // pow(blendWeights, 3);
// Force weights to sum to 1.0 (very important!)
blendWeights = max(blendWeights, real3(0.0, 0.0, 0.0));

62
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Editor/Material/Lit/LitUI.cs


public static GUIContent thicknessMapText = new GUIContent("Thickness map (R)", "If subsurface scattering is enabled, low values allow some light to be transmitted through the object.");
public static GUIContent thicknessRemapText = new GUIContent("Thickness Remap", "Remaps values of the thickness map from [0, 1] to the specified range.");
// Iridescence
public static GUIContent iridescenceMaskText = new GUIContent("Iridescence Mask", "Control intensity of the iridescence");
public static GUIContent thicknessIridescenceText = new GUIContent("Iridescence Thickness");
public static GUIContent thicknessMapIridescenceText = new GUIContent("Iridescence Thickness map");
public static GUIContent thicknessRemapIridescenceText = new GUIContent("Iridescence Thickness remap");
// Clear Coat
public static GUIContent coatMaskText = new GUIContent("Coat Mask", "Attenuate the coating effect (similar to change to IOR of 1");

// Transparency
public static string refractionModeText = "Refraction Mode";
public static GUIContent refractionIORText = new GUIContent("Index of refraction", "Index of refraction");
public static GUIContent refractionIorText = new GUIContent("Index of refraction", "Index of refraction");
public static GUIContent refractionThicknessText = new GUIContent("Refraction Thickness", "Thickness for rough refraction");
public static GUIContent refractionThicknessMultiplierText = new GUIContent("Refraction Thickness multiplier (m)", "Thickness multiplier");
public static GUIContent refractionThicknessMapText = new GUIContent("Refraction Thickness Map (R)", "Thickness multiplier");

protected MaterialProperty anisotropyMap = null;
protected const string kAnisotropyMap = "_AnisotropyMap";
protected MaterialProperty iridescenceMask = null;
protected const string kIridescenceMask = "_IridescenceMask";
protected MaterialProperty iridescenceMaskMap = null;
protected const string kIridescenceMaskMap = "_IridescenceMaskMap";
protected MaterialProperty thicknessIridescence = null;
protected const string kThicknessIridescence = "_ThicknessIridescence";
protected MaterialProperty thicknessMapIridescence = null;
protected const string kThicknessMapIridescence = "_ThicknessMapIridescence";
protected MaterialProperty thicknessRemapIridescence = null;
protected const string kThicknessRemapIridescence = "_ThicknessRemapIridescence";
protected MaterialProperty coatMask = null;
protected const string kCoatMask = "_CoatMask";
protected MaterialProperty coatMaskMap = null;

// transparency params
protected MaterialProperty ior = null;
protected const string kIOR = "_IOR";
protected const string kIor = "_Ior";
protected MaterialProperty transmittanceColor = null;
protected const string kTransmittanceColor = "_TransmittanceColor";
protected MaterialProperty transmittanceColorMap = null;

anisotropy = FindProperty(kAnisotropy, props);
anisotropyMap = FindProperty(kAnisotropyMap, props);
// Iridescence
iridescenceMask = FindProperty(kIridescenceMask, props);
iridescenceMaskMap = FindProperty(kIridescenceMaskMap, props);
thicknessIridescence = FindProperty(kThicknessIridescence, props);
thicknessMapIridescence = FindProperty(kThicknessMapIridescence, props);
thicknessRemapIridescence = FindProperty(kThicknessRemapIridescence, props);
// clear coat
coatMask = FindProperty(kCoatMask, props);
coatMaskMap = FindProperty(kCoatMaskMap, props);

transmittanceColorMap = FindProperty(kTransmittanceColorMap, props, false);
atDistance = FindProperty(kATDistance, props, false);
thicknessMultiplier = FindProperty(kThicknessMultiplier, props, false);
ior = FindProperty(kIOR, props, false);
ior = FindProperty(kIor, props, false);
// We reuse thickness from SSS
}

}
}
}
protected void ShaderIridescenceInputGUI()
{
m_MaterialEditor.TexturePropertySingleLine(Styles.iridescenceMaskText, iridescenceMaskMap, iridescenceMask);
m_MaterialEditor.TexturePropertySingleLine(Styles.thicknessMapIridescenceText, thicknessMapIridescence);
if (thicknessMapIridescence.textureValue != null)
{
// Display the remap of texture values.
Vector2 remap = thicknessRemapIridescence.vectorValue;
EditorGUI.BeginChangeCheck();
EditorGUILayout.MinMaxSlider(Styles.thicknessRemapIridescenceText, ref remap.x, ref remap.y, 0.0f, 1.0f);
if (EditorGUI.EndChangeCheck())
{
thicknessRemapIridescence.vectorValue = remap;
}
}
else
{
// Allow the user to set the constant value of thickness if no thickness map is provided.
m_MaterialEditor.ShaderProperty(thicknessIridescence, Styles.thicknessIridescenceText);
}
}
protected void ShaderClearCoatInputGUI()
{

m_MaterialEditor.TexturePropertySingleLine(Styles.baseColorText, baseColorMap[layerIndex], baseColor[layerIndex]);
if ((BaseLitGUI.MaterialId)materialID.floatValue == BaseLitGUI.MaterialId.LitStandard || (BaseLitGUI.MaterialId)materialID.floatValue == BaseLitGUI.MaterialId.LitAniso)
if ((BaseLitGUI.MaterialId)materialID.floatValue == BaseLitGUI.MaterialId.LitStandard ||
(BaseLitGUI.MaterialId)materialID.floatValue == BaseLitGUI.MaterialId.LitAniso ||
(BaseLitGUI.MaterialId)materialID.floatValue == BaseLitGUI.MaterialId.LitIridescence)
{
m_MaterialEditor.ShaderProperty(metallic[layerIndex], Styles.metallicText);
}

break;
case BaseLitGUI.MaterialId.LitSpecular:
ShaderSpecularColorInputGUI(material);
break;
case BaseLitGUI.MaterialId.LitIridescence:
ShaderIridescenceInputGUI();
break;
default:

var mode = (Lit.RefractionMode)refractionMode.floatValue;
if (mode != Lit.RefractionMode.None)
{
m_MaterialEditor.ShaderProperty(ior, Styles.refractionIORText);
m_MaterialEditor.ShaderProperty(ior, Styles.refractionIorText);
blendMode.floatValue = (float)BlendMode.Alpha;

CoreUtils.SetKeyword(material, "_DETAIL_MAP", material.GetTexture(kDetailMap));
CoreUtils.SetKeyword(material, "_SUBSURFACE_MASK_MAP", material.GetTexture(kSubsurfaceMaskMap));
CoreUtils.SetKeyword(material, "_THICKNESSMAP", material.GetTexture(kThicknessMap));
CoreUtils.SetKeyword(material, "_THICKNESSMAP_IRIDESCENCE", material.GetTexture(kThicknessMapIridescence));
CoreUtils.SetKeyword(material, "_SPECULARCOLORMAP", material.GetTexture(kSpecularColorMap));
bool needUV2 = (UVDetailMapping)material.GetFloat(kUVDetail) == UVDetailMapping.UV2 || (UVBaseMapping)material.GetFloat(kUVBase) == UVBaseMapping.UV2;

3
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/LayeredLit/LayeredLitData.hlsl


surfaceData.anisotropy = 0.0;
surfaceData.specularColor = float3(0.0, 0.0, 0.0);
surfaceData.coatMask = 0.0;
surfaceData.thicknessIrid = 0.0;
surfaceData.thicknessIridescence = 0.0;
surfaceData.iridescenceMask = 0.0;
// Transparency parameters
// Use thickness from SSS

8
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.cs


public float anisotropy; // anisotropic ratio(0->no isotropic; 1->full anisotropy in tangent direction, -1->full anisotropy in bitangent direction)
// Iridescence
public float thicknessIrid;
[SurfaceDataAttributes("Thickness of Iridescence")]
public float thicknessIridescence;
[SurfaceDataAttributes("Iridescence Mask")]
public float iridescenceMask;
// Forward property only

public float anisotropy;
// Iridescence
public float thicknessIrid;
public float thicknessIridescence;
public float iridescenceMask;
// ClearCoat
public float coatRoughness; // Automatically fill

42
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.cs.hlsl


#define DEBUGVIEW_LIT_SURFACEDATA_THICKNESS (1012)
#define DEBUGVIEW_LIT_SURFACEDATA_TANGENT (1013)
#define DEBUGVIEW_LIT_SURFACEDATA_ANISOTROPY (1014)
#define DEBUGVIEW_LIT_SURFACEDATA_THICKNESS_IRID (1015)
#define DEBUGVIEW_LIT_SURFACEDATA_INDEX_OF_REFRACTION (1016)
#define DEBUGVIEW_LIT_SURFACEDATA_TRANSMITTANCE_COLOR (1017)
#define DEBUGVIEW_LIT_SURFACEDATA_TRANSMITTANCE_ABSORPTION_DISTANCE (1018)
#define DEBUGVIEW_LIT_SURFACEDATA_TRANSMITTANCE_MASK (1019)
#define DEBUGVIEW_LIT_SURFACEDATA_THICKNESS_OF_IRIDESCENCE (1015)
#define DEBUGVIEW_LIT_SURFACEDATA_IRIDESCENCE_MASK (1016)
#define DEBUGVIEW_LIT_SURFACEDATA_INDEX_OF_REFRACTION (1017)
#define DEBUGVIEW_LIT_SURFACEDATA_TRANSMITTANCE_COLOR (1018)
#define DEBUGVIEW_LIT_SURFACEDATA_TRANSMITTANCE_ABSORPTION_DISTANCE (1019)
#define DEBUGVIEW_LIT_SURFACEDATA_TRANSMITTANCE_MASK (1020)
//
// UnityEngine.Experimental.Rendering.HDPipeline.Lit+BSDFData: static fields

#define DEBUGVIEW_LIT_BSDFDATA_ROUGHNESS_T (1045)
#define DEBUGVIEW_LIT_BSDFDATA_ROUGHNESS_B (1046)
#define DEBUGVIEW_LIT_BSDFDATA_ANISOTROPY (1047)
#define DEBUGVIEW_LIT_BSDFDATA_THICKNESS_IRID (1048)
#define DEBUGVIEW_LIT_BSDFDATA_COAT_ROUGHNESS (1049)
#define DEBUGVIEW_LIT_BSDFDATA_IOR (1050)
#define DEBUGVIEW_LIT_BSDFDATA_ABSORPTION_COEFFICIENT (1051)
#define DEBUGVIEW_LIT_BSDFDATA_TRANSMITTANCE_MASK (1052)
#define DEBUGVIEW_LIT_BSDFDATA_THICKNESS_IRIDESCENCE (1048)
#define DEBUGVIEW_LIT_BSDFDATA_IRIDESCENCE_MASK (1049)
#define DEBUGVIEW_LIT_BSDFDATA_COAT_ROUGHNESS (1050)
#define DEBUGVIEW_LIT_BSDFDATA_IOR (1051)
#define DEBUGVIEW_LIT_BSDFDATA_ABSORPTION_COEFFICIENT (1052)
#define DEBUGVIEW_LIT_BSDFDATA_TRANSMITTANCE_MASK (1053)
//
// UnityEngine.Experimental.Rendering.HDPipeline.Lit+GBufferMaterial: static fields

float thickness;
float3 tangentWS;
float anisotropy;
float thicknessIrid;
float thicknessIridescence;
float iridescenceMask;
float ior;
float3 transmittanceColor;
float atDistance;

float roughnessT;
float roughnessB;
float anisotropy;
float thicknessIrid;
float thicknessIridescence;
float iridescenceMask;
float coatRoughness;
float ior;
float3 absorptionCoefficient;

case DEBUGVIEW_LIT_SURFACEDATA_ANISOTROPY:
result = surfacedata.anisotropy.xxx;
break;
case DEBUGVIEW_LIT_SURFACEDATA_THICKNESS_IRID:
result = surfacedata.thicknessIrid.xxx;
case DEBUGVIEW_LIT_SURFACEDATA_THICKNESS_OF_IRIDESCENCE:
result = surfacedata.thicknessIridescence.xxx;
break;
case DEBUGVIEW_LIT_SURFACEDATA_IRIDESCENCE_MASK:
result = surfacedata.iridescenceMask.xxx;
break;
case DEBUGVIEW_LIT_SURFACEDATA_INDEX_OF_REFRACTION:
result = surfacedata.ior.xxx;

case DEBUGVIEW_LIT_BSDFDATA_ANISOTROPY:
result = bsdfdata.anisotropy.xxx;
break;
case DEBUGVIEW_LIT_BSDFDATA_THICKNESS_IRID:
result = bsdfdata.thicknessIrid.xxx;
case DEBUGVIEW_LIT_BSDFDATA_THICKNESS_IRIDESCENCE:
result = bsdfdata.thicknessIridescence.xxx;
break;
case DEBUGVIEW_LIT_BSDFDATA_IRIDESCENCE_MASK:
result = bsdfdata.iridescenceMask.xxx;
break;
case DEBUGVIEW_LIT_BSDFDATA_COAT_ROUGHNESS:
result = bsdfdata.coatRoughness.xxx;

173
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.hlsl


/* 19 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_PUNCTUAL | LIGHTFEATUREFLAGS_ENV | MATERIALFEATUREFLAGS_LIT_CLEAR_COAT | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 20 */ LIGHT_FEATURE_MASK_FLAGS_OPAQUE | MATERIALFEATUREFLAGS_LIT_CLEAR_COAT | MATERIALFEATUREFLAGS_LIT_STANDARD,
// Standard with clear coat and Iridescence
/* 21 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_PUNCTUAL | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_CLEAR_COAT | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 22 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_AREA | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_CLEAR_COAT | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 23 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_ENV | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_CLEAR_COAT | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 24 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_PUNCTUAL | LIGHTFEATUREFLAGS_ENV | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_CLEAR_COAT | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 25 */ LIGHT_FEATURE_MASK_FLAGS_OPAQUE | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_CLEAR_COAT | MATERIALFEATUREFLAGS_LIT_STANDARD,
// Standard with Iridescence
/* 21 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_PUNCTUAL | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 22 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_AREA | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 23 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_ENV | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 24 */ LIGHTFEATUREFLAGS_SKY | LIGHTFEATUREFLAGS_DIRECTIONAL | LIGHTFEATUREFLAGS_PUNCTUAL | LIGHTFEATUREFLAGS_ENV | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 25 */ LIGHT_FEATURE_MASK_FLAGS_OPAQUE | MATERIALFEATUREFLAGS_LIT_IRIDESCENCE | MATERIALFEATUREFLAGS_LIT_STANDARD,
/* 26 */ LIGHT_FEATURE_MASK_FLAGS_OPAQUE | MATERIAL_FEATURE_MASK_FLAGS, // Catch all case with MATERIAL_FEATURE_MASK_FLAGS is needed in case we disable material classification
};

// Helper functions/variable specific to this material
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
// Iridescence
//-----------------------------------------------------------------------------
// Ref: https://belcour.github.io/blog/research/2017/05/01/brdf-thin-film.html
// Evaluation XYZ sensitivity curves in Fourier space
float3 EvalSensitivity(float opd, float shift)
{
// Use Gaussian fits, given by 3 parameters: val, pos and var
float phase = 2.0 * PI * opd * 1e-6;
float3 val = float3(5.4856e-13, 4.4201e-13, 5.2481e-13);
float3 pos = float3(1.6810e+06, 1.7953e+06, 2.2084e+06);
float3 var = float3(4.3278e+09, 9.3046e+09, 6.6121e+09);
float3 xyz = val * sqrt(2.0 * PI * var) * cos(pos * phase + shift) * exp(-var * phase * phase);
xyz.x += 9.7470e-14 * sqrt(2.0 * PI * 4.5282e+09) * cos(2.2399e+06 * phase + shift) * exp(-4.5282e+09 * phase * phase);
return xyz / 1.0685e-7;
}
// Evaluate the reflectance for a thin-film layer on top of a dielectric medum.
float3 EvalIridescence(float eta_1, float cosTheta1, BSDFData bsdfData)
{
// thicknessIridescence unit is micrometer for this equation here. Mean 0.5 is 500nm.
float Dinc = 3.0 * bsdfData.thicknessIridescence;
// Note: Unlike the code provide with the paper, here we use schlick approximation
// Schlick is a very poor approximation when dealing with iridescence to the Fresnel
// term and there is no "neutral" value in this unlike in the original paper.
// We use Iridescence mask here to allow to have neutral value
// Hack: In order to use only one parameter (DInc), we deduced the ior of iridescence from current Dinc thicknessIridescence
// and we use mask instead to fade out the effect
float eta_2 = lerp(2.0, 1.0, bsdfData.thicknessIridescence);
// Following line from original code is not needed for us, it create a discontinuity
// Force eta_2 -> eta_1 when Dinc -> 0.0
// float eta_2 = lerp(eta_1, eta_2, smoothstep(0.0, 0.03, Dinc));
// Evaluate the cosTheta on the base layer (Snell law)
float cosTheta2 = sqrt(1.0 - Sq(eta_1 / eta_2) * (1.0 - Sq(cosTheta1)));
// First interface
float R0 = IorToFresnel0(eta_2, eta_1);
float R12 = F_Schlick(R0, cosTheta1);
float R21 = R12;
float T121 = 1.0 - R12;
float phi12 = 0.0;
float phi21 = PI - phi12;
// Second interface
float3 R23 = F_Schlick(bsdfData.fresnel0, cosTheta2);
float phi23 = 0.0;
// Phase shift
float OPD = Dinc * cosTheta2;
float phi = phi21 + phi23;
// Compound terms
float3 R123 = R12 * R23;
float3 r123 = sqrt(R123);
float3 Rs = Sq(T121) * R23 / (float3(1.0, 1.0, 1.0) - R123);
// Reflectance term for m = 0 (DC term amplitude)
float3 C0 = R12 + Rs;
float3 I = C0;
// Reflectance term for m > 0 (pairs of diracs)
float3 Cm = Rs - T121;
for (int m = 1; m <= 2; ++m)
{
Cm *= r123;
float3 Sm = 2.0 * EvalSensitivity(m * OPD, m * phi);
//vec3 SmP = 2.0 * evalSensitivity(m*OPD, m*phi2.y);
I += Cm * Sm;
}
// Convert back to RGB reflectance
//I = clamp(mul(I, XYZ_TO_RGB), float3(0.0, 0.0, 0.0), float3(1.0, 1.0, 1.0));
//I = mul(XYZ_TO_RGB, I);
return I;
}
#if HAS_REFRACTION
# include "CoreRP/ShaderLibrary/Refraction.hlsl"

bsdfData.bitangentWS = bitangentWS;
}
void FillMaterialIridescence(float thicknessIrid, inout BSDFData bsdfData)
void FillMaterialIridescence(float mask, float thickness, inout BSDFData bsdfData)
bsdfData.thicknessIrid = thicknessIrid;
bsdfData.iridescenceMask = mask;
bsdfData.thicknessIridescence = thickness;
}
// Note: this modify the parameter perceptualRoughness and fresnel0, so they need to be setup

float coatRoughnessScale = Sq(ieta);
float sigma = RoughnessToVariance(PerceptualRoughnessToRoughness(bsdfData.perceptualRoughness));
bsdfData.perceptualRoughness = RoughnessToPerceptualRoughness(VarianceToRoughness(sigma * coatRoughnessScale));
// Fresnel0 is deduced from interface between air and material (Assume to be 1.5 in Unity, or a metal).
// but here we go from clear coat (1.5) to material, we need to update fresnel0
// Note: Schlick is a poor approximation of Fresnel when ieta is 1 (1.5 / 1.5), schlick target 1.4 to 2.2 IOR.
bsdfData.fresnel0 = lerp(bsdfData.fresnel0, ConvertF0ForAirInterfaceToF0ForClearCoat15(bsdfData.fresnel0), coatMask);
}
void FillMaterialTransparencyData(float3 baseColor, float metallic, float ior, float3 transmittanceColor, float atDistance, float thickness, float transmittanceMask, inout BSDFData bsdfData)

// IOR define the fresnel0 value, so update it also for consistency (and even if not physical we still need to take into account any metal mask)
bsdfData.fresnel0 = lerp(IORToFresnel0(ior).xxx, baseColor, metallic);
bsdfData.fresnel0 = lerp(IorToFresnel0(ior).xxx, baseColor, metallic);
bsdfData.absorptionCoefficient = TransmittanceColorAtDistanceToAbsorption(transmittanceColor, atDistance);
bsdfData.transmittanceMask = transmittanceMask;

// Remap IOR in range 1..2.5 to 0..1
float RemapIor25to01(float ior)
{
return saturate((ior - 1.0) / 1.5);
}
float RemapIor01to25(float ior)
{
return ior * 1.5 + 1.0;
}
// For image based lighting, a part of the BSDF is pre-integrated.
// This is done both for specular and diffuse (in case of DisneyDiffuse)
void GetPreIntegratedFGD(float NdotV, float perceptualRoughness, float3 fresnel0, out float3 specularFGD, out float diffuseFGD, out float reflectivity)

if (HasFeatureFlag(surfaceData.materialFeatures, MATERIALFEATUREFLAGS_LIT_IRIDESCENCE))
{
FillMaterialIridescence(surfaceData.thicknessIrid, bsdfData);
FillMaterialIridescence(surfaceData.iridescenceMask, surfaceData.thicknessIridescence, bsdfData);
// Modify fresnel0 and perceptualRoughness
// Modify perceptualRoughness
FillMaterialClearCoatData(surfaceData.coatMask, bsdfData);
}

{
materialFeatureId = GBUFFER_LIT_IRIDESCENCE;
outGBuffer2.rgb = float3(0.0 /* TODO: IOR */, surfaceData.thicknessIrid,
outGBuffer2.rgb = float3(surfaceData.iridescenceMask, surfaceData.thicknessIridescence,
PackFloatInt8bit(surfaceData.metallic, 0, 8));
}
else // Standard

FillMaterialAnisotropy(anisotropy, frame[0], frame[1], bsdfData);
}
// The neutral value of iridescenceMask is 0 (handled by ZERO_INITIALIZE).
FillMaterialIridescence(inGBuffer2.g, bsdfData);
FillMaterialIridescence(inGBuffer2.r, inGBuffer2.g, bsdfData);
// Modify fresnel0 and perceptualRoughness
// Modify perceptualRoughness
FillMaterialClearCoatData(coatMask, bsdfData);
}

case DEBUGVIEW_LIT_SURFACEDATA_MATERIAL_FEATURES:
result = (surfaceData.materialFeatures.xxx) / 255.0; // Aloow to read with color picker debug mode
break;
case DEBUGVIEW_LIT_SURFACEDATA_INDEX_OF_REFRACTION:
result = RemapIor25to01(surfaceData.ior).xxx;
break;
}
}

case DEBUGVIEW_LIT_BSDFDATA_MATERIAL_FEATURES:
result = (bsdfData.materialFeatures.xxx) / 255.0; // Aloow to read with color picker debug mode
break;
case DEBUGVIEW_LIT_BSDFDATA_IOR:
result = RemapIor25to01(bsdfData.ior).xxx;
break;
}
}

float transparentSSMipLevel; // mip level of the screen space gaussian pyramid for rough refraction
};
PreLightData GetPreLightData(float3 V, PositionInputs posInput, BSDFData bsdfData)
PreLightData GetPreLightData(float3 V, PositionInputs posInput, inout BSDFData bsdfData)
{
PreLightData preLightData;
ZERO_INITIALIZE(PreLightData, preLightData);

float NdotV = ClampNdotV(preLightData.NdotV);
// We modify the bsdfData.fresnel0 here for iridescence
if (HasFeatureFlag(bsdfData.materialFeatures, MATERIALFEATUREFLAGS_LIT_IRIDESCENCE))
{
float viewAngle = NdotV;
float topIor = 1.0; // Default is air
if (HasFeatureFlag(bsdfData.materialFeatures, MATERIALFEATUREFLAGS_LIT_CLEAR_COAT))
{
topIor = lerp(1.0, CLEAR_COAT_IOR, bsdfData.coatMask);
// HACK: Use the reflected direction to specify the Fresnel coefficient for pre-convolved envmaps
viewAngle = sqrt(1.0 + Sq(1.0 / topIor) * (Sq(dot(bsdfData.normalWS, V)) - 1.0));
}
if (bsdfData.iridescenceMask > 0.0)
{
bsdfData.fresnel0 = lerp(bsdfData.fresnel0, EvalIridescence(topIor, viewAngle, bsdfData), bsdfData.iridescenceMask);
}
}
// We modify the bsdfData.fresnel0 here for clearCoat
// Fresnel0 is deduced from interface between air and material (Assume to be 1.5 in Unity, or a metal).
// but here we go from clear coat (1.5) to material, we need to update fresnel0
// Note: Schlick is a poor approximation of Fresnel when ieta is 1 (1.5 / 1.5), schlick target 1.4 to 2.2 IOR.
bsdfData.fresnel0 = lerp(bsdfData.fresnel0, ConvertF0ForAirInterfaceToF0ForClearCoat15(bsdfData.fresnel0), bsdfData.coatMask);
preLightData.coatPartLambdaV = GetSmithJointGGXPartLambdaV(NdotV, CLEAR_COAT_ROUGHNESS);
preLightData.coatIblR = reflect(-V, N);
preLightData.coatIblF = F_Schlick(CLEAR_COAT_F0, NdotV) * bsdfData.coatMask;

float NdotV = ClampNdotV(preLightData.NdotV);
float3 F = F_Schlick(bsdfData.fresnel0, LdotH);
float DV;
// Note: Here we are suppose to call EvalIridescence with LdotH
// This is to expensive for our need, so instead we use the NdotV
// Moreover, the bsdfData.fresnel0 here already contain the evaluation of F_Schlick
// in the context of iridescence, so if iridescence is enabled, don't apply schlick a second time
if (HasFeatureFlag(bsdfData.materialFeatures, MATERIALFEATUREFLAGS_LIT_IRIDESCENCE))
{
F = lerp(F, bsdfData.fresnel0, bsdfData.iridescenceMask);
}
float DV;
if (HasFeatureFlag(bsdfData.materialFeatures, MATERIALFEATUREFLAGS_LIT_ANISOTROPY))
{
float3 H = (L + V) * invLenLV;

if (_DebugLightingMode == DEBUGLIGHTINGMODE_LUX_METER)
{
// Only lighting, not BSDF
lighting.diffuse = color * intensity * lightData.diffuseScale;;
lighting.diffuse = color * intensity * lightData.diffuseScale;
}
#endif

if (_DebugLightingMode == DEBUGLIGHTINGMODE_LUX_METER)
{
// Only lighting, not BSDF
lighting.diffuse = color * intensity * lightData.diffuseScale;;
lighting.diffuse = color * intensity * lightData.diffuseScale;
}
#endif

9
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/Lit.shader


_ThicknessMap("Thickness Map", 2D) = "white" {}
_ThicknessRemap("Thickness Remap", Vector) = (0, 1, 0, 0)
_ThicknessIridescence("Thickness sridescence", Range(0.0, 1.0)) = 1.0
_ThicknessMapIridescence("Thickness Map Iridescence", 2D) = "white" {}
_ThicknessRemapIridescence("Thickness Remap Iridescence", Vector) = (0, 1, 0, 0)
_IridescenceMask("Iridescence Mask", Range(0.0, 1.0)) = 1.0
_IridescenceMaskMap("Iridescence Mask Map", 2D) = "white" {}
_CoatMask("Coat Mask", Range(0.0, 1.0)) = 0.0
_CoatMaskMap("CoatMaskMap", 2D) = "white" {}

// Transparency
[Enum(None, 0, Plane, 1, Sphere, 2)]_RefractionMode("Refraction Mode", Int) = 0
_IOR("Indice Of Refraction", Range(1.0, 2.5)) = 1.0
_Ior("Indice Of Refraction", Range(1.0, 2.5)) = 1.0
_ThicknessMultiplier("Thickness Multiplier", Float) = 1.0
_TransmittanceColor("Transmittance Color", Color) = (1.0, 1.0, 1.0)
_TransmittanceColorMap("TransmittanceColorMap", 2D) = "white" {}

#pragma shader_feature _DETAIL_MAP
#pragma shader_feature _SUBSURFACE_MASK_MAP
#pragma shader_feature _THICKNESSMAP
#pragma shader_feature _THICKNESSMAP_IRIDESCENCE
#pragma shader_feature _SPECULARCOLORMAP
#pragma shader_feature _TRANSMITTANCECOLORMAP

22
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/LitDataIndividualLayer.hlsl


#endif
#if HAS_REFRACTION
surfaceData.ior = _IOR;
surfaceData.ior = _Ior;
surfaceData.transmittanceColor *= SAMPLE_UVMAPPING_TEXTURE2D(ADD_IDX(_TransmittanceColorMap), ADD_ZERO_IDX(sampler_TransmittanceColorMap), ADD_IDX(layerTexCoord.base)).rgb;
surfaceData.transmittanceColor *= SAMPLE_UVMAPPING_TEXTURE2D(_TransmittanceColorMap, sampler_TransmittanceColorMap, ADD_IDX(layerTexCoord.base)).rgb;
#endif
surfaceData.atDistance = _ATDistance;

surfaceData.coatMask = 0.0;
#endif
surfaceData.thicknessIrid = 0.0;
#ifdef _MATERIAL_FEATURE_IRIDESCENCE
#ifdef _THICKNESSMAP_IRIDESCENCE
surfaceData.thicknessIridescence = SAMPLE_UVMAPPING_TEXTURE2D(_ThicknessMapIridescence, sampler_ThicknessMapIridescence, layerTexCoord.base).r;
surfaceData.thicknessIridescence = _ThicknessRemapIridescence.x + _ThicknessRemapIridescence.y * surfaceData.thicknessIridescence;
#else
surfaceData.thicknessIridescence = _ThicknessIridescence;
#endif
surfaceData.iridescenceMask = _IridescenceMask;
surfaceData.iridescenceMask *= SAMPLE_UVMAPPING_TEXTURE2D(_IridescenceMaskMap, sampler_IridescenceMaskMap, layerTexCoord.base).r;
#else
surfaceData.thicknessIridescence = 0.0;
surfaceData.iridescenceMask = 0.0;
#endif
#else // #if !defined(LAYERED_LIT_SHADER)

surfaceData.tangentWS = float3(0.0, 0.0, 0.0);
surfaceData.anisotropy = 0.0;
surfaceData.specularColor = float3(0.0, 0.0, 0.0);
surfaceData.thicknessIrid = 0.0;
surfaceData.thicknessIridescence = 0.0;
surfaceData.iridescenceMask = 0.0;
surfaceData.coatMask = 0.0;
// Transparency

13
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/LitProperties.hlsl


TEXTURE2D(_ThicknessMap);
SAMPLER(sampler_ThicknessMap);
TEXTURE2D(_ThicknessMapIridescence);
SAMPLER(sampler_ThicknessMapIridescence);
TEXTURE2D(_IridescenceMaskMap);
SAMPLER(sampler_IridescenceMaskMap);
TEXTURE2D(_SpecularColorMap);
SAMPLER(sampler_SpecularColorMap);

// Transparency
float3 _TransmittanceColor;
float _IOR;
float _Ior;
float _ATDistance;
float _ThicknessMultiplier;

float _SubsurfaceMask;
float _Thickness;
float4 _ThicknessRemap;
float _ThicknessIridescence;
float4 _ThicknessRemapIridescence;
float _IridescenceMask;
float _CoatMask;

10
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Lit/LitTessellation.shader


_ThicknessMap("Thickness Map", 2D) = "white" {}
_ThicknessRemap("Thickness Remap", Vector) = (0, 1, 0, 0)
_ThicknessIridescence("Thickness sridescence", Range(0.0, 1.0)) = 1.0
_ThicknessMapIridescence("Thickness Map Iridescence", 2D) = "white" {}
_ThicknessRemapIridescence("Thickness Remap Iridescence", Vector) = (0, 1, 0, 0)
_IridescenceMask("Iridescence Mask", Range(0.0, 1.0)) = 1.0
_IridescenceMaskMap("Iridescence Mask Map", 2D) = "white" {}
_CoatMask("Coat Mask", Range(0.0, 1.0)) = 0.0
_CoatMaskMap("CoatMaskMap", 2D) = "white" {}

// Transparency
[Enum(None, 0, Plane, 1, Sphere, 2)]_RefractionMode("Refraction Mode", Int) = 0
_IOR("Indice Of Refraction", Range(1.0, 2.5)) = 1.0
_Ior("Indice Of Refraction", Range(1.0, 2.5)) = 1.0
_ThicknessMultiplier("Thickness Multiplier", Float) = 1.0
_TransmittanceColor("Transmittance Color", Color) = (1.0, 1.0, 1.0)
_TransmittanceColorMap("TransmittanceColorMap", 2D) = "white" {}

#pragma shader_feature _DETAIL_MAP
#pragma shader_feature _SUBSURFACE_MASK_MAP
#pragma shader_feature _THICKNESSMAP
#pragma shader_feature _THICKNESSMAP_IRIDESCENCE
#pragma shader_feature _SPECULARCOLORMAP
#pragma shader_feature _TRANSMITTANCECOLORMAP

2
ScriptableRenderPipeline/HDRenderPipeline/HDRP/Material/Material.hlsl


#include "Lit/Lit.hlsl"
#elif defined(UNITY_MATERIAL_UNLIT)
#include "Unlit/Unlit.hlsl"
#elif defined(UNITY_MATERIAL_IRIDESCENCE)
//#include "Iridescence/Iridescence.hlsl"
#endif
//-----------------------------------------------------------------------------

正在加载...
取消
保存