Skip to content

Commit

Permalink
fix(postprocessing): use premult alpha (#277)
Browse files Browse the repository at this point in the history
  • Loading branch information
CodyJasonBennett authored Aug 6, 2023
1 parent 4c04593 commit e7dad43
Show file tree
Hide file tree
Showing 5 changed files with 21 additions and 23 deletions.
4 changes: 3 additions & 1 deletion src/postprocessing/EffectComposer.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Clock, LinearFilter, RGBAFormat, Vector2, WebGLRenderer, WebGLRenderTarget } from 'three'
import { Clock, LinearFilter, RGBAFormat, NoBlending, Vector2, WebGLRenderer, WebGLRenderTarget } from 'three'
import { CopyShader } from '../shaders/CopyShader'
import { ShaderPass } from './ShaderPass'
import { MaskPass, ClearMaskPass } from './MaskPass'
Expand Down Expand Up @@ -65,6 +65,8 @@ class EffectComposer<TRenderTarget extends WebGLRenderTarget = WebGLRenderTarget
}

this.copyPass = new ShaderPass(CopyShader)
// @ts-ignore
this.copyPass.material.blending = NoBlending

this.clock = new Clock()
}
Expand Down
22 changes: 3 additions & 19 deletions src/postprocessing/SSAARenderPass.js
Original file line number Diff line number Diff line change
@@ -1,14 +1,4 @@
import {
CustomBlending,
OneFactor,
AddEquation,
SrcAlphaFactor,
Color,
HalfFloatType,
ShaderMaterial,
UniformsUtils,
WebGLRenderTarget,
} from 'three'
import { AdditiveBlending, Color, HalfFloatType, ShaderMaterial, UniformsUtils, WebGLRenderTarget } from 'three'
import { Pass, FullScreenQuad } from './Pass'
import { CopyShader } from '../shaders/CopyShader'

Expand Down Expand Up @@ -47,14 +37,8 @@ class SSAARenderPass extends Pass {
transparent: true,
depthTest: false,
depthWrite: false,

// do not use AdditiveBlending because it mixes the alpha channel instead of adding
blending: CustomBlending,
blendEquation: AddEquation,
blendDst: OneFactor,
blendDstAlpha: OneFactor,
blendSrc: SrcAlphaFactor,
blendSrcAlpha: OneFactor,
premultipliedAlpha: true,
blending: AdditiveBlending,
})

this.fsQuad = new FullScreenQuad(this.copyMaterial)
Expand Down
3 changes: 2 additions & 1 deletion src/postprocessing/SavePass.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { ShaderMaterial, UniformsUtils, WebGLRenderTarget } from 'three'
import { NoBlending, ShaderMaterial, UniformsUtils, WebGLRenderTarget } from 'three'
import { Pass, FullScreenQuad } from './Pass'
import { CopyShader } from '../shaders/CopyShader'

Expand All @@ -18,6 +18,7 @@ class SavePass extends Pass {
uniforms: this.uniforms,
vertexShader: shader.vertexShader,
fragmentShader: shader.fragmentShader,
blending: NoBlending,
})

this.renderTarget = renderTarget
Expand Down
14 changes: 12 additions & 2 deletions src/postprocessing/TAARenderPass.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ class TAARenderPass extends SSAARenderPass {

this.sampleLevel = 0
this.accumulate = false
this.accumulateIndex = -1
}

render(renderer, writeBuffer, readBuffer, deltaTime) {
Expand Down Expand Up @@ -50,6 +51,9 @@ class TAARenderPass extends SSAARenderPass {
const autoClear = renderer.autoClear
renderer.autoClear = false

renderer.getClearColor(this._oldClearColor)
const oldClearAlpha = renderer.getClearAlpha()

const sampleWeight = 1.0 / jitterOffsets.length

if (this.accumulateIndex >= 0 && this.accumulateIndex < jitterOffsets.length) {
Expand All @@ -74,11 +78,16 @@ class TAARenderPass extends SSAARenderPass {
}

renderer.setRenderTarget(writeBuffer)
renderer.setClearColor(this.clearColor, this.clearAlpha)
renderer.clear()
renderer.render(this.scene, this.camera)

renderer.setRenderTarget(this.sampleRenderTarget)
if (this.accumulateIndex === 0) renderer.clear()
if (this.accumulateIndex === 0) {
renderer.setClearColor(0x000000, 0.0)
renderer.clear()
}

this.fsQuad.render(renderer)

this.accumulateIndex++
Expand All @@ -89,6 +98,7 @@ class TAARenderPass extends SSAARenderPass {
if (this.camera.clearViewOffset) this.camera.clearViewOffset()
}

renderer.setClearColor(this.clearColor, this.clearAlpha)
const accumulationWeight = this.accumulateIndex * sampleWeight

if (accumulationWeight > 0) {
Expand All @@ -103,11 +113,11 @@ class TAARenderPass extends SSAARenderPass {
this.copyUniforms['opacity'].value = 1.0 - accumulationWeight
this.copyUniforms['tDiffuse'].value = this.holdRenderTarget.texture
renderer.setRenderTarget(writeBuffer)
if (accumulationWeight === 0) renderer.clear()
this.fsQuad.render(renderer)
}

renderer.autoClear = autoClear
renderer.setClearColor(this._oldClearColor, oldClearAlpha)
}

dispose() {
Expand Down
1 change: 1 addition & 0 deletions src/postprocessing/TexturePass.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ class TexturePass extends Pass {
fragmentShader: shader.fragmentShader,
depthTest: false,
depthWrite: false,
premultipliedAlpha: true,
})

this.needsSwap = false
Expand Down

0 comments on commit e7dad43

Please sign in to comment.