{"version":3,"file":"SAOShader.cjs","sources":["../../src/shaders/SAOShader.ts"],"sourcesContent":["import { Matrix4, Vector2 } from 'three'\n\nimport type { IUniform, Texture } from 'three'\nimport type { IShader } from './types'\n\nexport type SAOShaderDefines = Record<\n  'DEPTH_PACKING' | 'DIFFUSE_TEXTURE' | 'NORMAL_TEXTURE' | 'NUM_RINGS' | 'NUM_SAMPLES' | 'PERSPECTIVE_CAMERA',\n  number\n>\n\nexport type SAOShaderUniforms = {\n  bias: IUniform<number>\n  cameraFar: IUniform<number>\n  cameraInverseProjectionMatrix: IUniform<Matrix4>\n  cameraNear: IUniform<number>\n  cameraProjectionMatrix: IUniform<Matrix4>\n  intensity: IUniform<number>\n  kernelRadius: IUniform<number>\n  minResolution: IUniform<number>\n  randomSeed: IUniform<number>\n  scale: IUniform<number>\n  size: IUniform<Vector2>\n  tDepth: IUniform<Texture | null>\n  tDiffuse: IUniform<Texture | null>\n  tNormal: IUniform<Texture | null>\n}\n\nexport interface ISAOShader extends IShader<SAOShaderUniforms, SAOShaderDefines> {\n  defines: SAOShaderDefines\n  needsUpdate?: boolean\n}\n\nexport const SAOShader: ISAOShader = {\n  defines: {\n    NUM_SAMPLES: 7,\n    NUM_RINGS: 4,\n    NORMAL_TEXTURE: 0,\n    DIFFUSE_TEXTURE: 0,\n    DEPTH_PACKING: 1,\n    PERSPECTIVE_CAMERA: 1,\n  },\n  uniforms: {\n    tDepth: { value: null },\n    tDiffuse: { value: null },\n    tNormal: { value: null },\n    size: { value: new Vector2(512, 512) },\n\n    cameraNear: { value: 1 },\n    cameraFar: { value: 100 },\n    cameraProjectionMatrix: { value: new Matrix4() },\n    cameraInverseProjectionMatrix: { value: new Matrix4() },\n\n    scale: { value: 1.0 },\n    intensity: { value: 0.1 },\n    bias: { value: 0.5 },\n\n    minResolution: { value: 0.0 },\n    kernelRadius: { value: 100.0 },\n    randomSeed: { value: 0.0 },\n  },\n  vertexShader: [\n    'varying vec2 vUv;',\n\n    'void main() {',\n    '\tvUv = uv;',\n    '\tgl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );',\n    '}',\n  ].join('\\n'),\n  fragmentShader: [\n    '#include <common>',\n\n    'varying vec2 vUv;',\n\n    '#if DIFFUSE_TEXTURE == 1',\n    'uniform sampler2D tDiffuse;',\n    '#endif',\n\n    'uniform sampler2D tDepth;',\n\n    '#if NORMAL_TEXTURE == 1',\n    'uniform sampler2D tNormal;',\n    '#endif',\n\n    'uniform float cameraNear;',\n    'uniform float cameraFar;',\n    'uniform mat4 cameraProjectionMatrix;',\n    'uniform mat4 cameraInverseProjectionMatrix;',\n\n    'uniform float scale;',\n    'uniform float intensity;',\n    'uniform float bias;',\n    'uniform float kernelRadius;',\n    'uniform float minResolution;',\n    'uniform vec2 size;',\n    'uniform float randomSeed;',\n\n    '// RGBA depth',\n\n    '#include <packing>',\n\n    'vec4 getDefaultColor( const in vec2 screenPosition ) {',\n    '\t#if DIFFUSE_TEXTURE == 1',\n    '\treturn texture2D( tDiffuse, vUv );',\n    '\t#else',\n    '\treturn vec4( 1.0 );',\n    '\t#endif',\n    '}',\n\n    'float getDepth( const in vec2 screenPosition ) {',\n    '\t#if DEPTH_PACKING == 1',\n    '\treturn unpackRGBAToDepth( texture2D( tDepth, screenPosition ) );',\n    '\t#else',\n    '\treturn texture2D( tDepth, screenPosition ).x;',\n    '\t#endif',\n    '}',\n\n    'float getViewZ( const in float depth ) {',\n    '\t#if PERSPECTIVE_CAMERA == 1',\n    '\treturn perspectiveDepthToViewZ( depth, cameraNear, cameraFar );',\n    '\t#else',\n    '\treturn orthographicDepthToViewZ( depth, cameraNear, cameraFar );',\n    '\t#endif',\n    '}',\n\n    'vec3 getViewPosition( const in vec2 screenPosition, const in float depth, const in float viewZ ) {',\n    '\tfloat clipW = cameraProjectionMatrix[2][3] * viewZ + cameraProjectionMatrix[3][3];',\n    '\tvec4 clipPosition = vec4( ( vec3( screenPosition, depth ) - 0.5 ) * 2.0, 1.0 );',\n    '\tclipPosition *= clipW; // unprojection.',\n\n    '\treturn ( cameraInverseProjectionMatrix * clipPosition ).xyz;',\n    '}',\n\n    'vec3 getViewNormal( const in vec3 viewPosition, const in vec2 screenPosition ) {',\n    '\t#if NORMAL_TEXTURE == 1',\n    '\treturn unpackRGBToNormal( texture2D( tNormal, screenPosition ).xyz );',\n    '\t#else',\n    '\treturn normalize( cross( dFdx( viewPosition ), dFdy( viewPosition ) ) );',\n    '\t#endif',\n    '}',\n\n    'float scaleDividedByCameraFar;',\n    'float minResolutionMultipliedByCameraFar;',\n\n    'float getOcclusion( const in vec3 centerViewPosition, const in vec3 centerViewNormal, const in vec3 sampleViewPosition ) {',\n    '\tvec3 viewDelta = sampleViewPosition - centerViewPosition;',\n    '\tfloat viewDistance = length( viewDelta );',\n    '\tfloat scaledScreenDistance = scaleDividedByCameraFar * viewDistance;',\n\n    '\treturn max(0.0, (dot(centerViewNormal, viewDelta) - minResolutionMultipliedByCameraFar) / scaledScreenDistance - bias) / (1.0 + pow2( scaledScreenDistance ) );',\n    '}',\n\n    '// moving costly divides into consts',\n    'const float ANGLE_STEP = PI2 * float( NUM_RINGS ) / float( NUM_SAMPLES );',\n    'const float INV_NUM_SAMPLES = 1.0 / float( NUM_SAMPLES );',\n\n    'float getAmbientOcclusion( const in vec3 centerViewPosition ) {',\n    '\t// precompute some variables require in getOcclusion.',\n    '\tscaleDividedByCameraFar = scale / cameraFar;',\n    '\tminResolutionMultipliedByCameraFar = minResolution * cameraFar;',\n    '\tvec3 centerViewNormal = getViewNormal( centerViewPosition, vUv );',\n\n    '\t// jsfiddle that shows sample pattern: https://jsfiddle.net/a16ff1p7/',\n    '\tfloat angle = rand( vUv + randomSeed ) * PI2;',\n    '\tvec2 radius = vec2( kernelRadius * INV_NUM_SAMPLES ) / size;',\n    '\tvec2 radiusStep = radius;',\n\n    '\tfloat occlusionSum = 0.0;',\n    '\tfloat weightSum = 0.0;',\n\n    '\tfor( int i = 0; i < NUM_SAMPLES; i ++ ) {',\n    '\t\tvec2 sampleUv = vUv + vec2( cos( angle ), sin( angle ) ) * radius;',\n    '\t\tradius += radiusStep;',\n    '\t\tangle += ANGLE_STEP;',\n\n    '\t\tfloat sampleDepth = getDepth( sampleUv );',\n    '\t\tif( sampleDepth >= ( 1.0 - EPSILON ) ) {',\n    '\t\t\tcontinue;',\n    '\t\t}',\n\n    '\t\tfloat sampleViewZ = getViewZ( sampleDepth );',\n    '\t\tvec3 sampleViewPosition = getViewPosition( sampleUv, sampleDepth, sampleViewZ );',\n    '\t\tocclusionSum += getOcclusion( centerViewPosition, centerViewNormal, sampleViewPosition );',\n    '\t\tweightSum += 1.0;',\n    '\t}',\n\n    '\tif( weightSum == 0.0 ) discard;',\n\n    '\treturn occlusionSum * ( intensity / weightSum );',\n    '}',\n\n    'void main() {',\n    '\tfloat centerDepth = getDepth( vUv );',\n    '\tif( centerDepth >= ( 1.0 - EPSILON ) ) {',\n    '\t\tdiscard;',\n    '\t}',\n\n    '\tfloat centerViewZ = getViewZ( centerDepth );',\n    '\tvec3 viewPosition = getViewPosition( vUv, centerDepth, centerViewZ );',\n\n    '\tfloat ambientOcclusion = getAmbientOcclusion( viewPosition );',\n\n    '\tgl_FragColor = getDefaultColor( vUv );',\n    '\tgl_FragColor.xyz *=  1.0 - ambientOcclusion;',\n    '}',\n  ].join('\\n'),\n}\n"],"names":["Vector2","Matrix4"],"mappings":";;;AAgCO,MAAM,YAAwB;AAAA,EACnC,SAAS;AAAA,IACP,aAAa;AAAA,IACb,WAAW;AAAA,IACX,gBAAgB;AAAA,IAChB,iBAAiB;AAAA,IACjB,eAAe;AAAA,IACf,oBAAoB;AAAA,EACtB;AAAA,EACA,UAAU;AAAA,IACR,QAAQ,EAAE,OAAO,KAAK;AAAA,IACtB,UAAU,EAAE,OAAO,KAAK;AAAA,IACxB,SAAS,EAAE,OAAO,KAAK;AAAA,IACvB,MAAM,EAAE,OAAO,IAAIA,MAAQ,QAAA,KAAK,GAAG,EAAE;AAAA,IAErC,YAAY,EAAE,OAAO,EAAE;AAAA,IACvB,WAAW,EAAE,OAAO,IAAI;AAAA,IACxB,wBAAwB,EAAE,OAAO,IAAIC,MAAAA,UAAU;AAAA,IAC/C,+BAA+B,EAAE,OAAO,IAAIA,MAAAA,UAAU;AAAA,IAEtD,OAAO,EAAE,OAAO,EAAI;AAAA,IACpB,WAAW,EAAE,OAAO,IAAI;AAAA,IACxB,MAAM,EAAE,OAAO,IAAI;AAAA,IAEnB,eAAe,EAAE,OAAO,EAAI;AAAA,IAC5B,cAAc,EAAE,OAAO,IAAM;AAAA,IAC7B,YAAY,EAAE,OAAO,EAAI;AAAA,EAC3B;AAAA,EACA,cAAc;AAAA,IACZ;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EAAA,EACA,KAAK,IAAI;AAAA,EACX,gBAAgB;AAAA,IACd;AAAA,IAEA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IAEA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IAEA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IAEA;AAAA,IACA;AAAA,IAEA;AAAA,IAEA;AAAA,IACA;AAAA,IACA;AAAA,EAAA,EACA,KAAK,IAAI;AACb;;"}