浏览代码

HDRenderPipeline: Third draft not working

/Branch_Batching2
Sebastien Lagarde 8 年前
当前提交
c4c5cfb5
共有 10 个文件被更改,包括 157 次插入24 次删除
  1. 1
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/LayeredLit/LayeredLit.shader
  2. 1
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/LayeredLit/LayeredLitTessellation.shader
  3. 3
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/Editor/BaseLitUI.cs
  4. 4
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/Editor/LitUI.cs
  5. 1
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/Lit.shader
  6. 166
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/LitData.hlsl
  7. 1
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/LitProperties.hlsl
  8. 1
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/LitTessellation.shader
  9. 2
      Assets/ScriptableRenderLoop/HDRenderPipeline/Material/SampleLayer.hlsl
  10. 1
      Assets/ScriptableRenderLoop/ShaderLibrary/PerPixelDisplacement.hlsl

1
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/LayeredLit/LayeredLit.shader


[ToggleOff] _EnablePerPixelDisplacement("Enable per pixel displacement", Float) = 0.0
_PPDMinSamples("Min sample for POM", Range(1.0, 64.0)) = 5
_PPDMaxSamples("Max sample for POM", Range(1.0, 64.0)) = 15
_PPDLodThreshold("Start lod to fade out the POM effect", Range(0.0, 16.0)) = 5
[Enum(DetailMapNormal, 0, DetailMapAOHeight, 1)] _DetailMapMode("DetailMap mode", Float) = 0
[Enum(Use Emissive Color, 0, Use Emissive Mask, 1)] _EmissiveColorMode("Emissive color mode", Float) = 1

1
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/LayeredLit/LayeredLitTessellation.shader


[ToggleOff] _EnablePerPixelDisplacement("Enable per pixel displacement", Float) = 0.0
_PPDMinSamples("Min sample for POM", Range(1.0, 64.0)) = 5
_PPDMaxSamples("Max sample for POM", Range(1.0, 64.0)) = 15
_PPDLodThreshold("Start lod to fade out the POM effect", Range(0.0, 16.0)) = 5
[Enum(DetailMapNormal, 0, DetailMapAOHeight, 1)] _DetailMapMode("DetailMap mode", Float) = 0
[Enum(Use Emissive Color, 0, Use Emissive Mask, 1)] _EmissiveColorMode("Emissive color mode", Float) = 1

3
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/Editor/BaseLitUI.cs


public static GUIContent enablePerPixelDisplacementText = new GUIContent("Enable Per Pixel Displacement", "");
public static GUIContent ppdMinSamplesText = new GUIContent("Minimum samples", "Minimun samples to use with per pixel displacement mapping");
public static GUIContent ppdMaxSamplesText = new GUIContent("Maximum samples", "Maximum samples to use with per pxiel displacement mapping");
public static GUIContent ppdLodThresholdText = new GUIContent("Fading LOD start", "Starting Lod where the parallax occlusion mapping effect start to disappear");
public static GUIContent detailMapModeText = new GUIContent("Detail Map with Normal", "Detail Map with AO / Height");
public static GUIContent UVDetailMappingText = new GUIContent("UV set for Detail", "");
public static GUIContent emissiveColorModeText = new GUIContent("Emissive Color Usage", "Use emissive color or emissive mask");

4
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/Editor/LitUI.cs


protected const string kPpdMinSamples = "_PPDMinSamples";
protected MaterialProperty ppdMaxSamples = null;
protected const string kPpdMaxSamples = "_PPDMaxSamples";
protected MaterialProperty ppdLodThreshold = null;
protected const string kPpdLodThreshold = "_PPDLodThreshold";
protected MaterialProperty detailMapMode = null;
protected const string kDetailMapMode = "_DetailMapMode";
protected MaterialProperty UVDetail = null;

enablePerPixelDisplacement = FindProperty(kEnablePerPixelDisplacement, props);
ppdMinSamples = FindProperty(kPpdMinSamples, props);
ppdMaxSamples = FindProperty(kPpdMaxSamples, props);
ppdLodThreshold = FindProperty(kPpdLodThreshold, props);
detailMapMode = FindProperty(kDetailMapMode, props);
emissiveColorMode = FindProperty(kEmissiveColorMode, props);
}

m_MaterialEditor.ShaderProperty(ppdMinSamples, Styles.ppdMinSamplesText);
m_MaterialEditor.ShaderProperty(ppdMaxSamples, Styles.ppdMaxSamplesText);
ppdMinSamples.floatValue = Mathf.Min(ppdMinSamples.floatValue, ppdMaxSamples.floatValue);
m_MaterialEditor.ShaderProperty(ppdLodThreshold, Styles.ppdLodThresholdText);
m_MaterialEditor.ShaderProperty(materialID, Styles.materialIDText);
m_MaterialEditor.ShaderProperty(subsurfaceProfile, Styles.subsurfaceProfileText);

1
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/Lit.shader


[ToggleOff] _EnablePerPixelDisplacement("Enable per pixel displacement", Float) = 0.0
_PPDMinSamples("Min sample for POM", Range(1.0, 64.0)) = 5
_PPDMaxSamples("Max sample for POM", Range(1.0, 64.0)) = 15
_PPDLodThreshold("Start lod to fade out the POM effect", Range(0.0, 16.0)) = 5
[Enum(DetailMapNormal, 0, DetailMapAOHeight, 1)] _DetailMapMode("DetailMap mode", Float) = 0
[Enum(UV0, 0, UV1, 1, UV2, 2, UV3, 3)] _UVDetail("UV Set for detail", Float) = 0
[HideInInspector] _UVDetailsMappingMask("_UVDetailsMappingMask", Color) = (1, 0, 0, 0)

166
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/LitData.hlsl


{
ZERO_INITIALIZE(LayerTexCoord, layerTexCoord);
bool isTriplanar = false;
#endif
bool isTriplanar = false;
#ifdef _MAPPING_TRIPLANAR
// Be sure that the compiler is aware that we don't touch UV1 to UV3 for main layer so it can optimize code
_UVMappingMask.yzw = float3(0.0, 0.0, 0.0);
ComputeLayerTexCoord( texCoord0, texCoord1, texCoord2, texCoord3,

float GetMaxDisplacement()
{
float maxDisplacement = 0.0;
#if defined(_HEIGHTMAP)
maxDisplacement = _HeightAmplitude0;
#endif
return maxDisplacement
}
// Return the minimun uv size for all layers including triplanar
float2 GetMinUvSize(LayerTexCoord layerTexCoord)
{
float2 minUvSize = float2(FLT_MAX, FLT_MAX);
#if defined(_HEIGHTMAP)
if (layerTexCoord.base0.isTriplanar)
{
minUvSize = min(layerTexCoord.base.uvYZ * _HeightMap_TexelSize.zw);
minUvSize = min(layerTexCoord.base.uvZX * _HeightMap_TexelSize.zw);
minUvSize = min(layerTexCoord.base.uvXY * _HeightMap_TexelSize.zw);
}
else
{
minUvSize = min(layerTexCoord.base.uv * _HeightMap_TexelSize.zw);
}
#endif
return minUvSize;
}
struct PerPixelHeightDisplacementParam
{
float2 uv;
};
// Calculate displacement for per vertex displacement mapping
float ComputePerPixelHeightDisplacement(float2 texOffsetCurrent, float lod, PerPixelHeightDisplacementParam param)
{
// Note: No multiply by amplitude here. This is include in the maxHeight provide to POM
// Tiling is automatically handled correctly here.
return SAMPLE_TEXTURE2D_LOD(_HeightMap0, sampler_ShareHeightMap, param.uv + texOffsetCurrent, lod).r;
}
#include "PerPixelDisplacement.hlsl"
#if defined(_HEIGHTMAP) && defined(_PER_PIXEL_DISPLACEMENT)
bool ppdEnable = false;
bool isPlanar = false;
bool isTriplanar = false;
// ref: https://www.gamedev.net/resources/_/technical/graphics-programming-and-theory/a-closer-look-at-parallax-occlusion-mapping-r3262
float3 viewDirTS = TransformWorldToTangent(V, input.tangentToWorld);
// Change the number of samples per ray depending on the viewing angle for the surface.
// Oblique angles require smaller step sizes to achieve more accurate precision for computing displacement.
int numSteps = (int)lerp(_PPDMaxSamples, _PPDMinSamples, viewDirTS.z);
#if defined(_PER_PIXEL_DISPLACEMENT) && defined(_HEIGHTMAP)
ppdEnable = true;
isPlanar = layerTexCoord.base0.isPlanar;
isTriplanar = layerTexCoord.base0.isTriplanar;
#endif
if (ppdEnable)
{
// See comment in layered version for details
float maxHeight = GetMaxDisplacement();
float2 minUvSize = GetMinUvSize(layerTexCoord);
float lod = ComputeTextureLOD(minUvSize);
ParallaxOcclusionMappingLayer(layerTexCoord, numSteps, viewDirTS);
PerPixelHeightDisplacementParam ppdParam;
// TODO: We are supposed to modify lightmaps coordinate (fetch in GetBuiltin), but this isn't the same uv mapping, so can't apply the offset here...
// Let's assume it will be "fine" as indirect diffuse is often low frequency
#endif
// We need to calculate the texture space direction. It depends on the mapping.
if (isTriplanar)
{
// TODO: implement. Require 3 call to POM + dedicated viewDirTS based on triplanar convention
// apply the 3 offset on all layers
/*
ppdParam.uv = layerTexCoord.base0.uvYZ;
float3 viewDirTS = ;
int numSteps = (int)lerp(_PPDMaxSamples, _PPDMinSamples, abs(viewDirTS.z));
ParallaxOcclusionMapping(float2 uv, lod, _PPDLodThreshold, numSteps, viewDirTS, maxHeight, ppdParam);
(...)
*/
}
else if (isPlanar) // Caution: this if is dynamic as planar is not a variant, should we do one ?
{
ppdParam.uv = layerTexCoord.base.uv;
// For planar the view vector is the world view vector (unless we want to support object triplanar ? and in this case used TransformWorldToObject)
// TODO: do we support object triplanar ? See ComputeLayerTexCoord
float3 viewDirTS = V;
int numSteps = (int)lerp(_PPDMaxSamples, _PPDMinSamples, viewDirTS.z);
float2 offset = ParallaxOcclusionMapping(float2 uv, lod, _PPDLodThreshold, numSteps, viewDirTS, maxHeight, ppdParam);
// Apply offset to all UVSet0
// _UVMappingPlanar0 will be 1.0 is UVSet0 is used;
layerTexCoord.base.uv += _UVMappingPlanar * offset;
layerTexCoord.details.uv += _UVMappingPlanar * offset;
}
else // UVSet0
{
ppdParam.uv = layerTexCoord.base.uv;
float3 viewDirTS = TransformWorldToTangent(V, input.tangentToWorld);
int numSteps = (int)lerp(_PPDMaxSamples, _PPDMinSamples, viewDirTS.z);
float2 offset = ParallaxOcclusionMapping(float2 uv, lod, _PPDLodThreshold, numSteps, viewDirTS, maxHeight, ppdParam);
// Apply offset to all UVSet0
// _UVMappingMask0.x will be 1.0 is UVSet0 is used;
layerTexCoord.base.uv += _UVMappingMask.x * offset;
layerTexCoord.details.uv += _UVDetailsMappingMask.x * offset;
}
}
return SampleHeightmapLod(layerTexCoord, lod, _HeightCenter, _HeightAmplitude);
return SAMPLE_LAYER_TEXTURE2D_LOD(_HeightMap, sampler_HeightMap, layerTexCoord.base, lod).r - _HeightCenter) * _HeightAmplitude;
}
void GetSurfaceAndBuiltinData(FragInputs input, float3 V, inout PositionInputs posInput, out SurfaceData surfaceData, out BuiltinData builtinData)

// Note: No multiply by amplitude here, this is bake into the weights and apply in BlendLayeredScalar
// The amplitude is normalize to be able to work with POM algorithm
// Tiling is automatically handled correctly here as we use 4 differents uv even if they come from the same UVSet (they include the tiling)
float height0 = SAMPLE_TEXTURE2D_LOD(_HeightMap0, sampler_ShareHeightMap, param.uv[0] + texOffsetCurrent, lod).r)
float height0 = SAMPLE_TEXTURE2D_LOD(_HeightMap0, sampler_ShareHeightMap, param.uv[0] + texOffsetCurrent, lod).r);
float height1 = SAMPLE_TEXTURE2D_LOD(_HeightMap1, sampler_ShareHeightMap, param.uv[1] + texOffsetCurrent, lod).r);
float height2 = SAMPLE_TEXTURE2D_LOD(_HeightMap2, sampler_ShareHeightMap, param.uv[2] + texOffsetCurrent, lod).r);
float height3 = SAMPLE_TEXTURE2D_LOD(_HeightMap3, sampler_ShareHeightMap, param.uv[3] + texOffsetCurrent, lod).r);

void ApplyPerPixelDisplacement(FragInputs input, float3 V, inout LayerTexCoord layerTexCoord)
{
bool ppdEnable = false;
bool isPlanar = false;
bool isTriplanar = false;
#if defined(_PER_PIXEL_DISPLACEMENT)
#if defined(_HEIGHTMAP0) || defined(_HEIGHTMAP1) || (_LAYER_COUNT >= 3 && defined(_HEIGHTMAP2)) || (_LAYER_COUNT >= 4 && defined(_HEIGHTMAP3))
#ifdef _PER_PIXEL_DISPLACEMENT
// To know if we are planar or triplanar just need to check if any of the active heightmap layer is true as they are enforce to be the same mapping
#if defined(_HEIGHTMAP0)
isPlanar = layerTexCoord.base0.isPlanar;
isTriplanar = layerTexCoord.base0.isTriplanar;
#if defined(_HEIGHTMAP1)
ppdEnable = true;
isPlanar = layerTexCoord.base1.isPlanar;
isTriplanar = layerTexCoord.base1.isTriplanar;
#if _LAYER_COUNT >= 3
#if defined(_HEIGHTMAP2)
ppdEnable = true;
isPlanar = layerTexCoord.base2.isPlanar;
isTriplanar = layerTexCoord.base2.isTriplanar;
#endif
#endif
#if _LAYER_COUNT >= 4
#if defined(_HEIGHTMAP3)
ppdEnable = true;
isPlanar = layerTexCoord.base3.isPlanar;
isTriplanar = layerTexCoord.base3.isTriplanar;
#endif
#endif
#endif // _PER_PIXEL_DISPLACEMENT
if (ppdEnable)
{
// Even if we use same mapping we can have different tiling. For per pixel displacement we will perform the ray marching with already tiled uv

}
ppdParam.mainHeightInfluence = 0.0;
#endif
layerTexCoord.base3
if (ppdlayerUV.triplanar)
if (isTriplanar)
{
// TODO: implement. Require 3 call to POM + dedicated viewDirTS based on triplanar convention
// apply the 3 offset on all layers

// Apply to all layer that used triplanar
*/
}
else if (ppdlayerUV.planar) // Caution: this if is dynamic as planar is not a variant, should we do one ?
else if (isPlanar) // Caution: this if is dynamic as planar is not a variant, should we do one ?
{
ppdParam.uv[0] = layerTexCoord.base0.uv;
ppdParam.uv[1] = layerTexCoord.base1.uv;

#endif
#endif
// Note: If per pixel displacement is enabled it mean we will fetch again the various heightmaps at the intersection location. Not sure the compiler can optimize.
float weights[_MAX_LAYER];
ComputeLayerWeights(input, layerTexCoord, float4(alpha0, alpha1, alpha2, alpha3), weights);

1
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/LitProperties.hlsl


float _PPDMaxSamples;
float _PPDMinSamples;
float _PPDLodThreshold;
#else // LAYERED_LIT_SHADER

1
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/Lit/LitTessellation.shader


[ToggleOff] _EnablePerPixelDisplacement("Enable per pixel displacement", Float) = 0.0
_PPDMinSamples("Min sample for POM", Range(1.0, 64.0)) = 5
_PPDMaxSamples("Max sample for POM", Range(1.0, 64.0)) = 15
_PPDLodThreshold("Start lod to fade out the POM effect", Range(0.0, 16.0)) = 5
[Enum(DetailMapNormal, 0, DetailMapAOHeight, 1)] _DetailMapMode("DetailMap mode", Float) = 0
[Enum(UV0, 0, UV1, 1, UV2, 2, UV3, 3)] _UVDetail("UV Set for detail", Float) = 0
[HideInInspector] _UVDetailsMappingMask("_UVDetailsMappingMask", Color) = (1, 0, 0, 0)

2
Assets/ScriptableRenderLoop/HDRenderPipeline/Material/SampleLayer.hlsl


// Gather all kind of mapping in one struct, allow to improve code readability
struct LayerUV
{
float2 uv;
float2 uv;
bool isPlanar; // mutually exclusive with isTriplanar
// triplanar
bool isTriplanar;

1
Assets/ScriptableRenderLoop/ShaderLibrary/PerPixelDisplacement.hlsl


// This function is compatible with tiled uv.
// it return the offset to apply to the UVSet provide in PerPixelHeightDisplacementParam
// viewDirTS is view vector in texture space matching the UVSet
// ref: https://www.gamedev.net/resources/_/technical/graphics-programming-and-theory/a-closer-look-at-parallax-occlusion-mapping-r3262
float2 ParallaxOcclusionMapping(float lod, float lodThreshold, int numSteps, float3 viewDirTS, float maxHeight, PerPixelHeightDisplacementParam ppdParam)
{
// Convention: 1.0 is top, 0.0 is bottom - POM is always inward, no extrusion

正在加载...
取消
保存