UNPKG

cione-comp-lib

Version:

`$ yarn add cione-comp-lib` 或者 `$ npm i cione-comp-lib -S`

112 lines (111 loc) 4.02 kB
import halton from "./halton.mjs"; import Pass from "../../../claygl/src/compositor/Pass.mjs"; import FrameBuffer from "../../../claygl/src/FrameBuffer.mjs"; import Texture2D from "../../../claygl/src/Texture2D.mjs"; import Shader from "../../../claygl/src/Shader.mjs"; import Matrix4 from "../../../claygl/src/math/Matrix4.mjs"; function TemporalSuperSampling(frames) { var haltonSequence = []; for (var i = 0; i < 30; i++) { haltonSequence.push([halton(i, 2), halton(i, 3)]); } this._haltonSequence = haltonSequence; this._frame = 0; this._sourceTex = new Texture2D(); this._sourceFb = new FrameBuffer(); this._sourceFb.attach(this._sourceTex); this._prevFrameTex = new Texture2D(); this._outputTex = new Texture2D(); var blendPass = this._blendPass = new Pass({ fragment: Shader.source("clay.compositor.blend") }); blendPass.material.disableTexturesAll(); blendPass.material.enableTexture(["texture1", "texture2"]); this._blendFb = new FrameBuffer({ depthBuffer: false }); this._outputPass = new Pass({ fragment: Shader.source("clay.compositor.output"), blendWithPrevious: true }); this._outputPass.material.define("fragment", "OUTPUT_ALPHA"); this._outputPass.material.blend = function(_gl) { _gl.blendEquationSeparate(_gl.FUNC_ADD, _gl.FUNC_ADD); _gl.blendFuncSeparate(_gl.ONE, _gl.ONE_MINUS_SRC_ALPHA, _gl.ONE, _gl.ONE_MINUS_SRC_ALPHA); }; } TemporalSuperSampling.prototype = { constructor: TemporalSuperSampling, jitterProjection: function(renderer, camera) { var viewport = renderer.viewport; var dpr = viewport.devicePixelRatio || renderer.getDevicePixelRatio(); var width = viewport.width * dpr; var height = viewport.height * dpr; var offset = this._haltonSequence[this._frame % this._haltonSequence.length]; var translationMat = new Matrix4(); translationMat.array[12] = (offset[0] * 2 - 1) / width; translationMat.array[13] = (offset[1] * 2 - 1) / height; Matrix4.mul(camera.projectionMatrix, translationMat, camera.projectionMatrix); Matrix4.invert(camera.invProjectionMatrix, camera.projectionMatrix); }, resetFrame: function() { this._frame = 0; }, getFrame: function() { return this._frame; }, getSourceFrameBuffer: function() { return this._sourceFb; }, getOutputTexture: function() { return this._outputTex; }, resize: function(width, height) { this._prevFrameTex.width = width; this._prevFrameTex.height = height; this._outputTex.width = width; this._outputTex.height = height; this._sourceTex.width = width; this._sourceTex.height = height; this._prevFrameTex.dirty(); this._outputTex.dirty(); this._sourceTex.dirty(); }, isFinished: function() { return this._frame >= this._haltonSequence.length; }, render: function(renderer, sourceTex, notOutput) { var blendPass = this._blendPass; if (this._frame === 0) { blendPass.setUniform("weight1", 0); blendPass.setUniform("weight2", 1); } else { blendPass.setUniform("weight1", 0.9); blendPass.setUniform("weight2", 0.1); } blendPass.setUniform("texture1", this._prevFrameTex); blendPass.setUniform("texture2", sourceTex || this._sourceTex); this._blendFb.attach(this._outputTex); this._blendFb.bind(renderer); blendPass.render(renderer); this._blendFb.unbind(renderer); if (!notOutput) { this._outputPass.setUniform("texture", this._outputTex); this._outputPass.render(renderer); } var tmp = this._prevFrameTex; this._prevFrameTex = this._outputTex; this._outputTex = tmp; this._frame++; }, dispose: function(renderer) { this._sourceFb.dispose(renderer); this._blendFb.dispose(renderer); this._prevFrameTex.dispose(renderer); this._outputTex.dispose(renderer); this._sourceTex.dispose(renderer); this._outputPass.dispose(renderer); this._blendPass.dispose(renderer); } }; export { TemporalSuperSampling as default };