// pxlNav Rendering Core
// Written by Kevin Edzenga; 2020,2024,2025
//
// Rendering core functions and management
// Handles render buffers and render loop
import {
Vector2,
ShaderMaterial,
FrontSide,
LinearSRGBColorSpace
} from "three";
import { EffectComposer, RenderPass, ShaderPass, CopyShader, UnrealBloomPass } from '../../libs/three/index.js';
import { ANTI_ALIASING } from "./Enums.js";
/**
* @namespace pxlRendering
* @description pxlNav Rendering
*/
export class Rendering{
constructor( pxlOptions ){
this.pxlOptions = pxlOptions;
this.pxlEnv = null;
this.pxlUser = null;
this.pxlUtils = null;
this.pxlTimer = null;
this.pxlQuality = null;
this.pxlDevice = null;
this.pxlCamera = null;
this.pxlShaders = null;
// Engine boots in `pxlNav.js` and is passed here
// It probably should boot here, but been refactoring for a while now
// It'll end up in this file eventually
this.engine = null;
this.scene = null;
this.shaderPasses={};
this.stepShaderFuncArr=[];
this.pxlRenderSettings={
'exposure':1.0,
'mult':1.0,
'bloomStrength':0.5,
'bloomThresh':.6,
'bloomRadius':.05,
}
// ## Move passes to a dict
this.mapMotionBlurPass=null;
this.mapOverlayHeavyPass=null;
this.mapOverlayPass=null;
this.mapOverlaySlimPass=null;
this.mapBoxAAPass=null;
this.mapCrossAAPass=null;
this.mapWorldPosMaterial=null;
this.mapGlowPass=null;
this.mapComposer=null;
this.mapComposerMotionBlur=null;
this.mapComposerGlow=null;
this.chromaticAberrationPass=null;
this.lizardKingPass=null;
this.mapComposerWarpPass=null;
this.blurScreenMerge=null;
}
init(){
}
setDependencies( pxlNav ){
this.scene=pxlNav.scene;
this.pxlEnv = pxlNav.pxlEnv;
this.pxlUser = pxlNav.pxlUser;
this.pxlUtils = pxlNav.pxlUtils;
this.pxlTimer = pxlNav.pxlTimer;
this.pxlQuality = pxlNav.pxlQuality;
this.pxlDevice = pxlNav.pxlDevice;
this.pxlCamera = pxlNav.pxlCamera;
this.pxlShaders = pxlNav.pxlShaders;
}
// Build composers and passes
/**
* @memberof pxlRendering
* @function buildComposers
* @description Build EffectComposers and ShaderPasses
*/
buildComposers(){
// Set up swapable frame buffers, for prior frame reads
/*EffectComposer.prototype.swapBuffer = ()=>{
let tmpBuffer = this.renderTarget2;
this.renderTarget2 = this.renderTarget1;
this.renderTarget1 = tmpBuffer;
};*/
///////////////////////////////////////////////////
// -- SCENE WIDE MATERIALS -- -- -- -- -- -- -- //
///////////////////////////////////////////////////
let near = this.pxlCamera.camera?.near || 0.1;
let far = this.pxlCamera.camera?.far || 1000;
this.mapWorldPosMaterial=new ShaderMaterial({
uniforms:{
camNear: { type:"f", value: near },
camFar: { type:"f", value: far }
},
vertexShader: this.pxlShaders.rendering.worldPositionVert(),
fragmentShader: this.pxlShaders.rendering.worldPositionFrag()
});
//this.mapWorldPosMaterial.side=DoubleSide;
this.mapWorldPosMaterial.side=FrontSide;
this.mapWorldPosMaterial.name="mapWorldPosMaterial";
///////////////////////////////////////////////////
// -- 2-Step Blur Composer -- -- -- -- -- -- -- //
///////////////////////////////////////////////////
/*
if( this.pxlOptions.postProcessPasses.roomBloomPass ){}
if( this.pxlOptions.postProcessPasses.motionBlurPass ){}
if( this.pxlOptions.postProcessPasses.mapComposerWarpPass ){}
if( this.pxlOptions.postProcessPasses.chromaticAberrationPass ){}
if( this.pxlOptions.postProcessPasses.lizardKingPass ){}
if( this.pxlOptions.postProcessPasses.starFieldPass ){}
if( this.pxlOptions.postProcessPasses.crystallinePass ){}
*/
if( this.pxlOptions.postProcessPasses.roomBloomPass ){
this.blurComposer = new EffectComposer(this.engine);
this.shaderPasses.blurXShaderPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
time:{ value:this.pxlTimer.msRunner },
tDiffuse: { value: null },
pDiffuse: { value: null },
resUV: { value: this.pxlDevice.screenRes },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.directionalBlurPass( "pDiffuse", [1,0], 4, 1.8 ),
defines: {}
} ), "tDiffuse"
);
this.shaderPasses.blurXShaderPass.material.uniforms.pDiffuse = this.pxlEnv.scene.renderGlowTarget.texture;
this.shaderPasses.blurXShaderPass.material.transparent = true;
this.shaderPasses.blurXShaderPass.needsSwap = true;
this.shaderPasses.blurXShaderPass.enabled=false;
this.shaderPasses.blurXShaderPass.name="blurXShaderPass";
this.blurComposer.addPass( this.shaderPasses.blurXShaderPass );
this.shaderPasses.dirBlurCopyPass = new ShaderPass(CopyShader);
this.shaderPasses.dirBlurCopyPass.enabled=false;
this.shaderPasses.dirBlurCopyPass.name="dirBlurCopyPass";
this.blurComposer.addPass(this.shaderPasses.dirBlurCopyPass);
this.shaderPasses.blurYShaderPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
time:{ value:this.pxlTimer.msRunner },
tDiffuse: { value: null },
//pDiffuse: { value: this.pxlEnv.scene.renderGlowTarget.texture },
//pDiffuse: { value: this.blurComposer.writeBuffer.texture },
pDiffuse: { value: null },
resUV: { value: this.pxlDevice.screenRes },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.directionalBlurPass( "pDiffuse", [0,1], 4, 1.3 ),
defines: {}
} ), "tDiffuse"
);
this.shaderPasses.blurYShaderPass.material.uniforms.pDiffuse = this.pxlEnv.scene.renderGlowTarget.texture;
this.shaderPasses.blurYShaderPass.material.transparent = true;
this.shaderPasses.blurYShaderPass.enabled=false;
this.shaderPasses.blurYShaderPass.name="blurYShaderPass";
this.blurComposer.addPass( this.shaderPasses.blurYShaderPass );
this.shaderPasses.scatterMixShaderPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
time:{ value:this.pxlTimer.msRunner },
tDiffuse: { value: null },
pDiffuse: { value: null },
resUV: { value: this.pxlDevice.screenRes },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.mixBlurShaderPass(),
defines: {}
} ), "tDiffuse"
);
this.shaderPasses.scatterMixShaderPass.material.uniforms.pDiffuse = this.pxlEnv.scene.renderGlowTarget.texture;
this.shaderPasses.scatterMixShaderPass.material.transparent = true;
this.shaderPasses.scatterMixShaderPass.enabled=false;
this.shaderPasses.scatterMixShaderPass.name="scatterMixShaderPass";
this.blurComposer.addPass( this.shaderPasses.scatterMixShaderPass );
// Set Anti-Aliasing Quality
if( this.pxlOptions.antiAliasing===ANTI_ALIASING.LOW){
this.shaderPasses.scatterMixShaderPass.enabled=true;
}else if( this.pxlOptions.antiAliasing===ANTI_ALIASING.MEDIUM){
this.shaderPasses.blurXShaderPass.enabled=true;
this.shaderPasses.dirBlurCopyPass.enabled=true;
this.shaderPasses.blurYShaderPass.enabled=true;
}else if( this.pxlOptions.antiAliasing===ANTI_ALIASING.HIGH ){
this.shaderPasses.blurXShaderPass.enabled=true;
this.shaderPasses.dirBlurCopyPass.enabled=true;
this.shaderPasses.blurYShaderPass.enabled=true;
this.shaderPasses.scatterMixShaderPass.enabled=true;
}
}
///////////////////////////////////////////////////
// -- POST PROCESSING; MAIN MENU -- -- -- -- -- //
///////////////////////////////////////////////////
// Post Processing
this.mapComposerMotionBlur=new EffectComposer(this.engine);
this.mapMotionBlurPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
rDiffuse: { value: null },
exposure:{type:"f",value:this.pxlRenderSettings.exposure},
time:{ value:this.pxlTimer.msRunner },
camRotXYZ:{ value:this.pxlCamera.camRotXYZ },
blurDirCur:{ type:'f',value:this.blurDirCur },
blurDirPrev:{ type:'f',value:this.blurDirPrev },
noiseTexture: { value: this.pxlEnv.cloud3dTexture },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.motionBlurPostProcess(this.pxlDevice.screenRes,this.pxlDevice.mobile),
defines: {}
} ), "tDiffuse"
);
this.mapMotionBlurPass.material.uniforms.rDiffuse = this.pxlEnv.scene.renderTarget.texture;
this.mapMotionBlurPass.needsSwap = true;
this.mapMotionBlurPass.name = "mapMotionBlurPass";
this.mapComposerMotionBlur.addPass(this.mapMotionBlurPass);
this.mapMotionBlurPass.enabled=false;
this.mapComposerMotionBlur.renderToScreen=false;
//this.mapComposerMotionBlur.autoClear=false;
// -- -- -- -- -- -- -- -- -- -- //
this.mapComposerGlow=new EffectComposer(this.engine);
let renderGlowPass = new RenderPass(this.pxlEnv.scene, this.pxlCamera.camera);
this.mapComposerGlow.addPass(renderGlowPass);
this.blurScreenMerge = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
rDiffuse: { value: null },
mtDiffuse: { value: null },
exposure:{type:"f",value:this.pxlRenderSettings.exposure}
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.compLayersPostProcess(),
defines: {}
} ), "tDiffuse"
);
this.blurScreenMerge.material.uniforms.rDiffuse = this.pxlEnv.scene.renderTarget.texture;
// TODO : Motion Blur pass, performance is slow but should be enableable through 'options'
//this.blurScreenMerge.material.uniforms.mtDiffuse = this.mapComposerMotionBlur.renderTarget2.texture;
this.blurScreenMerge.material.uniforms.mtDiffuse = this.pxlEnv.scene.renderTarget.texture;
this.blurScreenMerge.needsSwap = true;
this.blurScreenMerge.name = "blurScreenMerge";
this.mapComposerGlow.addPass(this.blurScreenMerge);
let glowCopyPassBlur = new ShaderPass(CopyShader);
glowCopyPassBlur.name = "glowCopyPassBlur";
this.mapComposerGlow.addPass(glowCopyPassBlur);
//this.mapGlowPass = new UnrealBloomPass( new Vector2( this.pxlDevice.mapW*this.pxlQuality.bloomPercMult, this.pxlDevice.mapH*this.pxlQuality.bloomPercMult ), .28, 0.08, 0.13 );
//this.mapGlowPass.threshold = this.pxlRenderSettings.bloomThresh;
//this.mapGlowPass.strength = this.pxlRenderSettings.bloomStrength;
//this.mapGlowPass.radius = this.pxlRenderSettings.bloomRadius;
/*this.mapGlowPass = new BloomPass( this.pxlRenderSettings.bloomStrength, 50, 4, 512);
this.mapGlowPass.threshold = this.pxlRenderSettings.bloomThresh;
this.mapGlowPass.strength = this.pxlRenderSettings.bloomStrength;
this.mapGlowPass.radius = this.pxlRenderSettings.bloomRadius;*/
//this.mapGlowPass.clear=true;
//this.mapComposerGlow.addPass(this.mapGlowPass);
this.mapComposerGlow.renderToScreen=false;
this.mapComposerGlow.autoClear=true;
this.mapOverlayHeavyPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
gamma:{type:"f",value:this.pxlDevice.gammaCorrection},
exposure:{type:"f",value:this.pxlRenderSettings.exposure},
time:{ value:this.pxlTimer.msRunner },
camPos: { value: this.pxlCamera.camera.position },
ratio:{ type:'f',value: 1 },
tDiffuse: { value: null },
rDiffuse: { value: null },
bloomTexture: { value: null },
sceneDepth: { value: null },
scenePos: { value: null },
noiseTexture: { value: this.pxlEnv.cloud3dTexture },
fogMult: { value: this.fogMult },
proximityMult: { value: 1 },
//bloomTexture: { value: this.mapComposerMotionBlur.renderTarget2.texture }
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.finalOverlayHeavyShader(),
defines: {}
} ), "tDiffuse"
);
this.mapOverlayHeavyPass.material.uniforms.rDiffuse = this.pxlEnv.scene.renderTarget.texture;
this.mapOverlayHeavyPass.material.uniforms.bloomTexture = this.mapComposerGlow.renderTarget2.texture;
this.mapOverlayHeavyPass.material.uniforms.sceneDepth = this.pxlEnv.scene.renderTarget.depthTexture;
this.mapOverlayHeavyPass.material.uniforms.scenePos = this.pxlEnv.scene.renderWorldPos.texture;
this.mapOverlayHeavyPass.needsSwap = true;
this.mapOverlayHeavyPass.name = "mapOverlayHeavyPass";
this.mapOverlayPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
gamma:{type:"f",value:this.pxlDevice.gammaCorrection},
exposure:{type:"f",value:this.pxlRenderSettings.exposure},
time:{ value:this.pxlTimer.msRunner },
camPos: { value: this.pxlCamera.camera.position },
ratio:{ type:'f',value: 1 },
tDiffuse: { value: null },
rDiffuse: { value: null },
bloomTexture: { value: null },
sceneDepth: { value: null },
scenePos: { value: null },
noiseTexture: { value: this.pxlEnv.cloud3dTexture },
fogMult: { value: this.fogMult },
proximityMult: { value: 1 },
//bloomTexture: { value: this.mapComposerMotionBlur.renderTarget2.texture }
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.finalOverlayShader(),
defines: {}
} ), "tDiffuse"
);
this.mapOverlayPass.material.uniforms.rDiffuse = this.pxlEnv.scene.renderTarget.texture;
this.mapOverlayPass.material.uniforms.bloomTexture = this.mapComposerGlow.renderTarget2.texture;
this.mapOverlayPass.material.uniforms.sceneDepth = this.pxlEnv.scene.renderTarget.depthTexture;
this.mapOverlayPass.material.uniforms.scenePos = this.pxlEnv.scene.renderWorldPos.texture;
this.mapOverlayPass.needsSwap = true;
this.mapOverlayPass.name = "mapOverlayPass";
this.mapOverlaySlimPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
gamma:{type:"f",value:this.pxlDevice.gammaCorrection},
exposure:{type:"f",value:this.pxlRenderSettings.exposure},
time:{ value:this.pxlTimer.msRunner },
camPos: { value: this.pxlCamera.camera.position },
ratio:{ type:'f',value: 1 },
tDiffuse: { value: null },
rDiffuse: { value: null },
bloomTexture: { value: null },
sceneDepth: { value: null },
fogMult: { value: this.fogMult },
proximityMult: { value: 1 },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.finalOverlaySlimShader(),
defines: {}
} ), "tDiffuse"
);
this.mapOverlaySlimPass.material.uniforms.rDiffuse = this.pxlEnv.scene.renderTarget.texture;
//bloomTexture: { value: this.mapComposerMotionBlur.renderTarget2.texture }
this.mapOverlaySlimPass.material.uniforms.bloomTexture = this.mapComposerGlow.renderTarget2.texture;
this.mapOverlaySlimPass.material.uniforms.sceneDepth = this.pxlEnv.scene.renderTarget.depthTexture;
this.mapOverlaySlimPass.needsSwap = true;
this.mapOverlaySlimPass.name = "mapOverlaySlimPass";
// -- -- -- -- -- -- -- -- -- -- //
this.mapGlowPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
time:{ value:this.pxlTimer.msRunner },
ratio:{ type:'f',value: 1 },
tDiffuse: { value: null },
rDiffuse: { value: null },
sceneDepth: { value: null },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.glowPassPostProcess(),
defines: {}
} ), "tDiffuse"
);
this.mapGlowPass.material.uniforms.rDiffuse = this.pxlEnv.scene.renderGlowTarget.texture;
this.mapGlowPass.material.uniforms.sceneDepth = this.pxlEnv.scene.renderTarget.depthTexture;
this.mapGlowPass.needsSwap = true;
this.mapGlowPass.name = "mapGlowPass";
// -- -- -- -- -- -- -- -- -- -- //
this.mapComposer = new EffectComposer(this.engine);
this.mapComposer.addPass( this.mapOverlayHeavyPass );
this.mapComposer.addPass( this.mapOverlayPass );
this.mapComposer.addPass( this.mapOverlaySlimPass );
this.mapComposer.addPass( this.mapGlowPass );
this.mapOverlayHeavyPass.enabled=false;
this.mapOverlayPass.enabled=false;
//this.mapOverlayPass.autoClear=true;
//this.mapOverlaySlimPass.enabled=false;
// -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- //
this.pxlUser.lKingWarp=new Vector2( ...this.pxlUser.lKingInactive );
this.lizardKingPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
time:{ value:this.pxlTimer.msRunner },
ratio: { value: this.pxlDevice.screenRes },
noiseTexture: { value: this.pxlEnv.cloud3dTexture },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.lKingPostProcess(),
defines: {}
} ), "tDiffuse"
);
this.pxlUser.lizardKingPass=this.lizardKingPass;
this.lizardKingPass.enabled=false;
this.pxlUser.lizardKingPass.name = "lizardKingPass";
// -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- //
this.pxlUser.starFieldPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
time:{ value:this.pxlTimer.msRunner },
ratio: { value: this.pxlDevice.screenRes },
noiseTexture: { value: this.pxlEnv.cloud3dTexture },
starTexture: { value: this.pxlUtils.loadTexture(this.pxlUtils.assetRoot+"uv_starNoise.jpg", null, {"encoding":LinearSRGBColorSpace}) },
},
vertexShader: this.pxlShaders.rendering.sFieldPostProcessVert(),
fragmentShader: this.pxlShaders.rendering.sFieldPostProcessFrag(),
defines: {}
} ), "tDiffuse"
);
this.pxlUser.starFieldPass.enabled=false;
this.pxlUser.starFieldPass.name = "starFieldPass";
// -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- //
this.pxlUser.crystallinePass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
tDiffusePrev: {type:'t', value: null },
time:{ value:this.pxlTimer.msRunner },
ratio: { value: this.pxlDevice.screenRes },
noiseTexture: { value: this.pxlEnv.cloud3dTexture },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.iZoomPostProcess(),
defines: {}
} ), "tDiffuse"
);
this.pxlUser.crystallinePass.enabled=false;
this.pxlUser.crystallinePass.name = "crystallinePass";
// -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- //
if( this.pxlOptions.postProcessPasses.chromaticAberrationPass ){
this.chromaticAberrationPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
ratio: { value: this.pxlDevice.screenRes },
warpMult: { value: this.chroAberMult },
chroAberUVTexture: { value: this.chroAberUVTexture },
chroAberUVAlpha: { value: this.chroAberUVAlpha },
lKing: { value: this.pxlUser.lKingWarp },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.chroAberPostProcess(),
defines: {}
} ), "tDiffuse"
);
this.chromaticAberrationPass.enabled=false;
this.chromaticAberrationPass.name = "chromaticAberrationPass";
this.mapComposer.addPass( this.chromaticAberrationPass );
}
if( this.pxlOptions.postProcessPasses.lizardKingPass ){
this.mapComposer.addPass( this.lizardKingPass );
}
//if( !this.mobile ) {
if( this.pxlOptions.postProcessPasses.starFieldPass ){
this.mapComposer.addPass( this.pxlUser.starFieldPass );
}
if( this.pxlOptions.postProcessPasses.crystallinePass ){
this.mapComposer.addPass( this.pxlUser.crystallinePass );
}
if( this.pxlOptions.postProcessPasses.mapComposerWarpPass ){
this.mapComposerWarpPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
time:{ value:this.pxlTimer.msRunner },
fader:{ value:this.pxlEnv.warpVisualFader },
tDiffuse: { value: null },
noiseTexture: { value: this.pxlEnv.cloud3dTexture },
animTexture: { value: this.pxlEnv.blockAnimTexture },
//bloomTexture: { value: this.mapComposerMotionBlur.renderTarget2.texture }
},
vertexShader: this.pxlShaders.core.camPosVert(),
fragmentShader: this.pxlShaders.rendering.warpPostProcess(),
defines: {}
} ), "tDiffuse"
);
this.mapComposerWarpPass.needsSwap = true;
this.mapComposerWarpPass.enabled=false;
this.mapComposerWarpPass.name = "mapComposerWarpPass";
this.mapComposer.addPass( this.mapComposerWarpPass );
}
// 8 Samples
this.mapBoxAAPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
resUV:{ type:'f',value:this.pxlDevice.screenRes },
ratio:{ type:'f',value: 1 },
gamma:{type:"f",value:this.pxlDevice.gammaCorrection},
},
vertexShader: this.pxlShaders.core.camPosVert(),
fragmentShader: this.pxlShaders.rendering.boxAntiAliasPass(),
defines: {}
} ), "tDiffuse"
);
this.mapBoxAAPass.enabled=false;
this.mapBoxAAPass.name = "mapBoxAAPass";
this.mapComposer.addPass( this.mapBoxAAPass );
// 4 samples
this.mapCrossAAPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
resUV:{ type:'f',value:this.pxlDevice.screenRes },
ratio:{ type:'f',value: 1 },
gamma:{type:"f",value:this.pxlDevice.gammaCorrection},
},
vertexShader: this.pxlShaders.core.camPosVert(),
fragmentShader: this.pxlShaders.rendering.crossAntiAliasPass(),
defines: {}
} ), "tDiffuse"
);
this.mapCrossAAPass.enabled=false;
this.mapCrossAAPass.name = "mapCrossAAPass";
this.mapComposer.addPass( this.mapCrossAAPass );
this.mapComposer.autoClear=true;
// -- -- -- -- -- -- -- -- -- -- //
// External Room composer
let bootScene= this.pxlEnv.roomSceneList[this.pxlEnv.bootRoom].scene; // this.pxlEnv.roomSceneList['ShadowPlanet'].scene ||
this.roomComposer=new EffectComposer(this.engine);
this.roomRenderPass = new RenderPass(bootScene, this.pxlCamera.camera);
this.roomRenderPass.name = "roomRenderPass";
this.roomComposer.addPass(this.roomRenderPass);
this.pxlEnv.roomNameList.forEach( (r)=>{
if( r !== this.mainRoom){
let curPass=this.pxlEnv.roomSceneList[ r ].applyRoomPass( this.roomComposer );
if( curPass ){
curPass.enabled=false;
this.roomComposer.addPass( curPass );
}
}
});
this.roomBloomPass = new UnrealBloomPass( new Vector2( this.pxlDevice.mapW*.5, this.pxlDevice.mapH*.5 ), 1.5, 0.8, 0.85 );
this.roomBloomPass.threshold = this.pxlRenderSettings.bloomThresh;
this.roomBloomPass.strength = this.pxlRenderSettings.bloomStrength;
this.roomBloomPass.radius = this.pxlRenderSettings.bloomRadius;
this.roomBloomPass.name = "roomBloomPass";
this.roomComposer.addPass( this.roomBloomPass );
if( this.pxlOptions.postProcessPasses.roomGlowPass ){
this.roomGlowPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
time:{ value:this.pxlTimer.msRunner },
ratio:{ type:'f',value: 1 },
tDiffuse: { value: null },
gDiffuse: { value: null },
rDiffuse: { value: null },
sceneDepth: { value: null },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.glowPassPostProcess(),
defines: {}
} ), "tDiffuse"
);
//gDiffuse: { value: this.pxlEnv.scene.renderGlowTarget.texture },
//gDiffuse: { value: this.blurComposer.renderTarget1.texture },
this.roomGlowPass.material.uniforms.gDiffuse = this.blurComposer.writeBuffer.texture;
this.roomGlowPass.material.uniforms.rDiffuse = this.blurComposer.renderTarget2.texture;
this.roomGlowPass.material.uniforms.sceneDepth = this.pxlEnv.scene.renderTarget.depthTexture;
this.roomGlowPass.needsSwap = true;
this.roomGlowPass.name = "roomGlowPass";
this.roomComposer.addPass( this.roomGlowPass );
}
if( this.pxlOptions.postProcessPasses.chromaticAberrationPass ){
this.roomComposer.addPass( this.chromaticAberrationPass );
}
if( this.pxlOptions.postProcessPasses.lizardKingPass ){
this.roomComposer.addPass( this.lizardKingPass );
}
if( this.pxlOptions.postProcessPasses.starFieldPass ){
this.roomComposer.addPass( this.pxlUser.starFieldPass );
}
if( this.pxlOptions.postProcessPasses.crystallinePass ){
this.roomComposer.addPass( this.pxlUser.crystallinePass );
}
if( this.pxlOptions.postProcessPasses.mapComposerWarpPass ){
this.roomComposer.addPass( this.mapComposerWarpPass );
}
this.roomComposer.addPass( this.mapCrossAAPass );
this.roomComposer.addPass( this.mapBoxAAPass );
this.roomComposer.autoClear=true;
// -- -- -- -- -- -- -- -- //
// -- -- -- -- -- -- -- -- //
// Set above, for pass to use renderTarget in uniforms
this.delayComposer=new EffectComposer(this.engine);
//let renderDelayPass = new RenderPass(this.pxlEnv.scene, this.pxlCamera.camera);
//this.delayComposer.addPass(renderDelayPass);
this.delayPass = new ShaderPass(
new ShaderMaterial( {
uniforms: {
tDiffuse: { value: null },
roomComposer: { type:"f", value : 0 },
tDiffusePrev: { value: null },
tDiffusePrevRoom: { value: null },
},
vertexShader: this.pxlShaders.core.defaultVert(),
fragmentShader: this.pxlShaders.rendering.textureStorePass(),
defines: {}
} ), "tDiffuse"
);
this.delayPass.material.uniforms.tDiffusePrev = this.mapComposer.renderTarget1.texture;
this.delayPass.material.uniforms.tDiffusePrevRoom = this.roomComposer.renderTarget1.texture;
//this.delayPass.needsSwap = true;
this.delayPass.clear=false;
this.delayComposer.addPass( this.delayPass );
this.delayComposer.renderToScreen=false;
this.delayComposer.autoClear=false;
this.pxlUser.crystallinePass.uniforms.tDiffusePrev.value = this.delayComposer.renderTarget2.texture;
}
/**
*
* @param {*} canvasW
* @param {*} canvasH
*/
resize( canvasW, canvasH ){
if( this.pxlEnv.mapComposer ) this.pxlEnv.mapComposer.setSize(canvasW,canvasH);
if( this.pxlEnv.mapComposerGlow ) this.pxlEnv.mapComposerGlow.setSize(canvasW,canvasH);
// For external rooms --
if( this.pxlEnv.roomComposer ){
this.pxlEnv.roomComposer.setSize( canvasW, canvasH);
}
if( this.pxlEnv.roomGlowPass ){
this.pxlEnv.roomGlowPass.setSize(canvasW*this.pxlQuality.bloomPercMult,canvasH*this.pxlQuality.bloomPercMult);
}
// -- -- -- -- -- -- --
// For texture swapping --
if( this.pxlEnv.delayComposer ) this.pxlEnv.delayComposer.setSize(canvasW,canvasH);
// -- -- -- -- -- -- --
if( this.pxlEnv.mapGlowPass ){
this.pxlEnv.mapGlowPass.setSize(canvasW*this.pxlQuality.bloomPercMult,canvasH*this.pxlQuality.bloomPercMult);
}
if( this.pxlEnv.mapMotionBlurPass ){
this.pxlEnv.mapMotionBlurPass.setSize(canvasW*this.pxlQuality.mBlurPercMult,canvasH*this.pxlQuality.mBlurPercMult);
}
if( this.pxlEnv.mapOverlayHeavyPass ){
this.pxlEnv.mapOverlayHeavyPass.setSize(canvasW,canvasH);
this.pxlEnv.mapOverlayHeavyPass.uniforms.ratio.value = Math.min( 1, canvasW/canvasH );
}
if( this.pxlEnv.mapOverlayPass ){
this.pxlEnv.mapOverlayPass.setSize(canvasW,canvasH);
this.pxlEnv.mapOverlayPass.uniforms.ratio.value = Math.min( 1, canvasW/canvasH );
}
if( this.pxlEnv.mapOverlaySlimPass ){
this.pxlEnv.mapOverlaySlimPass.setSize(canvasW,canvasH);
this.pxlEnv.mapOverlaySlimPass.uniforms.ratio.value = Math.min( 1, canvasW/canvasH );
}
}
// -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- //
// -- Render & Buffer Helper Functions -- -- -- //
// -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- //
// Set composer uniforms
/**
* @memberof pxlRendering
* @function updateCompUniforms
* @description Update the exposure uniform for the rendering composers
* @param {number} exposure
*/
updateCompUniforms(exposure=null){
if(exposure){
this.pxlRenderSettings.exposure=exposure*this.pxlRenderSettings.mult;
}
if(this.mapOverlayPass){
this.mapMotionBlurPass.uniforms.exposure.value = this.pxlRenderSettings.exposure;
this.mapOverlayHeavyPass.uniforms.exposure.value = this.pxlRenderSettings.exposure;
this.mapOverlayPass.uniforms.exposure.value = this.pxlRenderSettings.exposure;
this.mapOverlaySlimPass.uniforms.exposure.value = this.pxlRenderSettings.exposure;
//this.blurScreenMerge.uniforms.exposure.value = this.pxlRenderSettings.exposure;
}
}
// TODO : Re-implement to room passes
// It got disconnected during refactor
/**
* @memberof pxlRendering
* @function stepShaderValues
* @description Step shader variables for shaders that need to update values each frame
*/
stepShaderValues(){ // ## Switch variables in shaders to three variables to avoid this whole thing
this.stepShaderFuncArr.forEach((x)=>{
if(typeof(x)=="object"){
x.step();
}else if(typeof(x)=="string"){
//console.log("shader trigger?");
//console.log(x);
//(x);
}
});
}
}