12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576 |
- // Do not edit.
- import { ShaderStore } from "../Engines/shaderStore.js";
- import "./ShadersInclude/fibonacci.js";
- import "./ShadersInclude/helperFunctions.js";
- import "./ShadersInclude/subSurfaceScatteringFunctions.js";
- import "./ShadersInclude/diffusionProfile.js";
- const name = "subSurfaceScatteringPixelShader";
- const shader = `#include<fibonacci>
- #include<helperFunctions>
- #include<subSurfaceScatteringFunctions>
- #include<diffusionProfile>
- varying vec2 vUV;uniform vec2 texelSize;uniform sampler2D textureSampler;uniform sampler2D irradianceSampler;uniform sampler2D depthSampler;uniform sampler2D albedoSampler;uniform vec2 viewportSize;uniform float metersPerUnit;const float LOG2_E=1.4426950408889634;const float SSS_PIXELS_PER_SAMPLE=4.;const int _SssSampleBudget=40;
- #define rcp(x) 1./x
- #define Sq(x) x*x
- #define SSS_BILATERAL_FILTER true
- vec3 EvalBurleyDiffusionProfile(float r,vec3 S)
- {vec3 exp_13=exp2(((LOG2_E*(-1.0/3.0))*r)*S);
- vec3 expSum=exp_13*(1.+exp_13*exp_13);
- return (S*rcp(8.*PI))*expSum; }
- vec2 SampleBurleyDiffusionProfile(float u,float rcpS)
- {u=1.-u;
- float g=1.+(4.*u)*(2.*u+sqrt(1.+(4.*u)*u));float n=exp2(log2(g)*(-1.0/3.0));
- float p=(g*n)*n;
- float c=1.+p+n;
- float d=(3./LOG2_E*2.)+(3./LOG2_E)*log2(u);
- float x=(3./LOG2_E)*log2(c)-d;
- float rcpExp=((c*c)*c)*rcp((4.*u)*((c*c)+(4.*u)*(4.*u)));float r=x*rcpS;float rcpPdf=(8.*PI*rcpS)*rcpExp;
- return vec2(r,rcpPdf);}
- vec3 ComputeBilateralWeight(float xy2,float z,float mmPerUnit,vec3 S,float rcpPdf)
- {
- #ifndef SSS_BILATERAL_FILTER
- z=0.;
- #endif
- float r=sqrt(xy2+(z*mmPerUnit)*(z*mmPerUnit));float area=rcpPdf;
- #if SSS_CLAMP_ARTIFACT
- return clamp(EvalBurleyDiffusionProfile(r,S)*area,0.0,1.0);
- #else
- return EvalBurleyDiffusionProfile(r,S)*area;
- #endif
- }
- void EvaluateSample(int i,int n,vec3 S,float d,vec3 centerPosVS,float mmPerUnit,float pixelsPerMm,
- float phase,inout vec3 totalIrradiance,inout vec3 totalWeight)
- {float scale =rcp(float(n));float offset=rcp(float(n))*0.5;float sinPhase,cosPhase;sinPhase=sin(phase);cosPhase=cos(phase);vec2 bdp=SampleBurleyDiffusionProfile(float(i)*scale+offset,d);float r=bdp.x;float rcpPdf=bdp.y;float phi=SampleDiskGolden(i,n).y;float sinPhi,cosPhi;sinPhi=sin(phi);cosPhi=cos(phi);float sinPsi=cosPhase*sinPhi+sinPhase*cosPhi;
- float cosPsi=cosPhase*cosPhi-sinPhase*sinPhi;
- vec2 vec=r*vec2(cosPsi,sinPsi);vec2 position;
- float xy2;position=vUV+round((pixelsPerMm*r)*vec2(cosPsi,sinPsi))*texelSize;xy2 =r*r;vec4 textureSample=texture2D(irradianceSampler,position);float viewZ=texture2D(depthSampler,position).r;vec3 irradiance =textureSample.rgb;if (testLightingForSSS(textureSample.a))
- {float relZ=viewZ-centerPosVS.z;vec3 weight=ComputeBilateralWeight(xy2,relZ,mmPerUnit,S,rcpPdf);totalIrradiance+=weight*irradiance;totalWeight +=weight;}
- else
- {}}
- #define CUSTOM_FRAGMENT_DEFINITIONS
- void main(void)
- {vec4 irradianceAndDiffusionProfile =texture2D(irradianceSampler,vUV);vec3 centerIrradiance=irradianceAndDiffusionProfile.rgb;int diffusionProfileIndex=int(round(irradianceAndDiffusionProfile.a*255.));float centerDepth =0.;vec4 inputColor=texture2D(textureSampler,vUV);bool passedStencilTest=testLightingForSSS(irradianceAndDiffusionProfile.a);if (passedStencilTest)
- {centerDepth=texture2D(depthSampler,vUV).r;}
- if (!passedStencilTest) {
- gl_FragColor=inputColor;return;}
- float distScale =1.;vec3 S =diffusionS[diffusionProfileIndex];float d =diffusionD[diffusionProfileIndex];float filterRadius=filterRadii[diffusionProfileIndex];vec2 centerPosNDC=vUV;vec2 cornerPosNDC=vUV+0.5*texelSize;vec3 centerPosVS =vec3(centerPosNDC*viewportSize,1.0)*centerDepth;
- vec3 cornerPosVS =vec3(cornerPosNDC*viewportSize,1.0)*centerDepth;
- float mmPerUnit =1000.*(metersPerUnit*rcp(distScale));float unitsPerMm=rcp(mmPerUnit);float unitsPerPixel=2.*abs(cornerPosVS.x-centerPosVS.x);float pixelsPerMm =rcp(unitsPerPixel)*unitsPerMm;float filterArea =PI*Sq(filterRadius*pixelsPerMm);int sampleCount =int(filterArea*rcp(SSS_PIXELS_PER_SAMPLE));int sampleBudget=_SssSampleBudget;int texturingMode=0;vec3 albedo =texture2D(albedoSampler,vUV).rgb;if (distScale==0. || sampleCount<1)
- {
- #ifdef DEBUG_SSS_SAMPLES
- vec3 green=vec3(0.,1.,0.);gl_FragColor=vec4(green,1.0);return;
- #endif
- gl_FragColor=vec4(inputColor.rgb+albedo*centerIrradiance,1.0);return;}
- #ifdef DEBUG_SSS_SAMPLES
- vec3 red =vec3(1.,0.,0.);vec3 blue=vec3(0.,0.,1.);gl_FragColor=vec4(mix(blue,red,clamp(float(sampleCount)/float(sampleBudget),0.0,1.0)),1.0);return;
- #endif
- float phase=0.;int n=min(sampleCount,sampleBudget);vec3 centerWeight =vec3(0.);
- vec3 totalIrradiance=vec3(0.);vec3 totalWeight =vec3(0.);for (int i=0; i<n; i++)
- {EvaluateSample(i,n,S,d,centerPosVS,mmPerUnit,pixelsPerMm,
- phase,totalIrradiance,totalWeight);}
- totalWeight=max(totalWeight,HALF_MIN);gl_FragColor=vec4(inputColor.rgb+albedo*max(totalIrradiance/totalWeight,vec3(0.0)),1.);}`;
- // Sideeffect
- ShaderStore.ShadersStore[name] = shader;
- /** @internal */
- export const subSurfaceScatteringPixelShader = { name, shader };
- //# sourceMappingURL=subSurfaceScattering.fragment.js.map
|