const OIT_LAYER=4,OIT_GLSL_TAIL=`
  {
    float oitZ = 1.0 / gl_FragCoord.w;
    float oitA = clamp(gl_FragColor.a, 0.0, 1.0);
    float oitW = oitA * clamp(0.03 / (1e-5 + pow(oitZ / 200.0, 4.0)), 1e-2, 3e3);
    oitWeight = vec4(oitW, 0.0, 0.0, 1.0);
    gl_FragColor = vec4(gl_FragColor.rgb * oitW, oitA);
  }
}`;function _setSharedBlend(n){n.blending=THREE.CustomBlending,n.blendEquation=THREE.AddEquation,n.blendEquationAlpha=THREE.AddEquation,n.blendSrc=THREE.OneFactor,n.blendDst=THREE.OneFactor,n.blendSrcAlpha=THREE.ZeroFactor,n.blendDstAlpha=THREE.OneMinusSrcAlphaFactor,n.premultipliedAlpha=!1,n.transparent=!0,n.depthWrite=!1}class OITPass{constructor(e){this.renderer=e,this.tsl=!!(window.GFX&&window.GFX.tsl),this.enabled=!0,this.scale=1,this.profile=null,this.profileOn=!1,this.rt=null,this.w=0,this.h=0,this.variants=new Map,this.set=[],this.lastCount=0,this.depthMat=this.tsl?new THREE.MeshBasicNodeMaterial({colorWrite:!1,fog:!1}):new THREE.MeshBasicMaterial({colorWrite:!1}),this.depthMat.name="oit_depth_only",this.tsl?this._initTSL():this._initGLSL()}ensureRT(){const e=this.renderer,i=Math.max(2,Math.round(e.domElement.width*this.scale)),r=Math.max(2,Math.round(e.domElement.height*this.scale));if(this.rt&&this.w===i&&this.h===r)return;this.rt&&this.rt.dispose();const t={count:2,type:THREE.HalfFloatType,format:THREE.RGBAFormat,depthBuffer:!0,stencilBuffer:!1,minFilter:THREE.NearestFilter,magFilter:THREE.NearestFilter,generateMipmaps:!1};this.rt=this.tsl?new THREE.RenderTarget(i,r,t):new THREE.WebGLRenderTarget(i,r,t),this.rt.textures[0].name="accum",this.rt.textures[1].name="weight";for(const s of this.rt.textures)s.colorSpace=THREE.NoColorSpace;this.w=i,this.h=r,this.tsl?(this.compMat.colorNode=null,this.compMat.opacityNode=null,this._bindTSLComposite()):(this.compMat.uniforms.tAccum.value=this.rt.textures[0],this.compMat.uniforms.tWeight.value=this.rt.textures[1],this.compMat.uniforms.uRes.value.set(e.domElement.width,e.domElement.height))}_initGLSL(){this.compMat=new THREE.ShaderMaterial({uniforms:{tAccum:{value:null},tWeight:{value:null},uRes:{value:new THREE.Vector2(1,1)}},vertexShader:"void main(){ gl_Position = vec4(position.xy, 0.0, 1.0); }",fragmentShader:`
        uniform sampler2D tAccum; uniform sampler2D tWeight; uniform vec2 uRes;
        void main(){
          vec2 uv = gl_FragCoord.xy / uRes;
          vec4 a = texture2D(tAccum, uv);
          float wsum = texture2D(tWeight, uv).r;
          vec3 col = a.rgb / max(wsum, 1e-5);
          float alpha = 1.0 - clamp(a.a, 0.0, 1.0);
          gl_FragColor = vec4(col, alpha);
          #include <tonemapping_fragment>
          #include <colorspace_fragment>
        }`,transparent:!0,depthTest:!1,depthWrite:!1,blending:THREE.NormalBlending,toneMapped:!0}),this.quadScene=new THREE.Scene;const e=new THREE.Mesh(new THREE.PlaneGeometry(2,2),this.compMat);e.frustumCulled=!1,this.quadScene.add(e),this.quadCam=new THREE.OrthographicCamera(-1,1,1,-1,0,1)}_variantOf(e){let i=this.variants.get(e.uuid);if(i&&i.userData.srcVersion!==e.version&&(i.dispose(),this.variants.delete(e.uuid),i=null),!i){const r=e.isShaderMaterial?e.uniforms:null;r&&(e.uniforms={}),i=e.clone(),r&&(e.uniforms=r,i.uniforms=r),_setSharedBlend(i);const t=e.onBeforeCompile;i.onBeforeCompile=(s,o)=>{t&&t.call(e,s,o),s.fragmentShader=`layout(location = 1) out highp vec4 oitWeight;
`+s.fragmentShader.replace(/}\s*$/,OIT_GLSL_TAIL)},i.customProgramCacheKey=()=>(e.customProgramCacheKey?e.customProgramCacheKey():"")+"|wboit",i.userData.oitVariant=!0,i.userData.srcVersion=e.version,i.name=(e.name||"mat")+"_oit",this.variants.set(e.uuid,i)}return i.opacity=e.opacity,i.side=e.side,i.visible=e.visible,i.color&&e.color&&i.color.copy(e.color),e.clippingPlanes!==void 0&&(i.clippingPlanes=e.clippingPlanes),i}_initTSL(){const e=window.TSL,i=e.positionView.z.negate(),r=e.float(.03).div(i.div(200).pow(4).add(1e-5)).clamp(.01,3e3),t=e.output.a.clamp(0,1),s=t.mul(r);this.mrtNode=e.mrt({accum:e.vec4(e.output.rgb.mul(s),t),weight:e.vec4(s,0,0,1)}),this.mrtNode.setBlendMode("accum",new THREE.BlendMode(THREE.MaterialBlending)),this.mrtNode.setBlendMode("weight",new THREE.BlendMode(THREE.MaterialBlending)),this.compMat=new THREE.MeshBasicNodeMaterial({transparent:!0,depthTest:!1,depthWrite:!1,blending:THREE.NormalBlending,fog:!1}),this.quad=new THREE.QuadMesh(this.compMat)}_bindTSLComposite(){const e=window.TSL,r=window.BLOOD_SHELL_TSL&&window.BLOOD_SHELL_TSL.thickFlipY?e.vec2(e.screenUV.x,e.screenUV.y.oneMinus()):e.screenUV,t=e.texture(this.rt.textures[0],r),s=e.texture(this.rt.textures[1],r).r;this.compMat.colorNode=t.rgb.div(s.max(1e-5)),this.compMat.opacityNode=t.a.clamp(0,1).oneMinus(),this.compMat.needsUpdate=!0}collect(e){const i=[];return e.traverse(r=>{if(!r.isMesh||r.isPoints||!r.visible)return;const t=r.material;!t||Array.isArray(t)||!t.transparent||t.visible===!1||r.userData.morphFollower||r.userData.oitSkip||r.userData.sectionCap||r.name.endsWith("_blood")||t.userData&&(t.userData.oitSkip||t.userData.sectionCap)||i.push({obj:r,mat:t})}),i}render(e,i,r){const t=this.renderer,s=this.set=this.collect(r);if(this.lastCount=s.length,!s.length){t.render(e,i);return}this.ensureRT();const o=this.profileOn?{main:0,depth:0,oit:0,comp:0}:null;let h=o?performance.now():0;for(const a of s)a.obj.visible=!1;t.render(e,i),o&&(o.main=performance.now()-h,h=performance.now());const c=t.getRenderTarget(),u=i.layers.mask,p=e.overrideMaterial,f=t.autoClear,m=e.background,d=new THREE.Color,E=t.getClearAlpha();t.getClearColor(d),t.setRenderTarget(this.rt),t.setClearColor(0,1),t.autoClear=!1,t.clear(!0,!0,!1),e.background=null,this.tsl&&t.setMRT(this.mrtNode),e.overrideMaterial=this.depthMat,t.render(e,i),e.overrideMaterial=null,o&&(o.depth=performance.now()-h,h=performance.now());for(const a of s)if(a.obj.visible=!0,a.obj.layers.enable(4),this.tsl){const l=a.mat;a.saved={blending:l.blending,blendEquation:l.blendEquation,blendEquationAlpha:l.blendEquationAlpha,blendSrc:l.blendSrc,blendDst:l.blendDst,blendSrcAlpha:l.blendSrcAlpha,blendDstAlpha:l.blendDstAlpha,premultipliedAlpha:l.premultipliedAlpha,depthWrite:l.depthWrite},_setSharedBlend(l)}else a.obj.material=this._variantOf(a.mat);i.layers.set(4),t.render(e,i),o&&(o.oit=performance.now()-h,h=performance.now());for(const a of s)a.obj.layers.disable(4),this.tsl?Object.assign(a.mat,a.saved):a.obj.material=a.mat;this.tsl&&t.setMRT(null),i.layers.mask=u,e.overrideMaterial=p,e.background=m,t.setClearColor(d,E),t.setRenderTarget(c),t.autoClear=!1,this.tsl?this.quad.render(t):t.render(this.quadScene,this.quadCam),t.autoClear=f,o&&(o.comp=performance.now()-h,this.profile=o)}dispose(){this.rt&&this.rt.dispose();for(const e of this.variants.values())e.dispose();this.variants.clear(),this.compMat.dispose(),this.depthMat.dispose()}}Object.assign(window,{OITPass,OIT_LAYER:4});
