浏览代码

TSL: Vertex shader revision (#30108)

* vertex shader revision

* revision

* cleanup

* Update Three.TSL.js

* Update webgpu_instance_sprites.jpg

* Update webgpu_tsl_galaxy.jpg

* renames
sunag 1 年之前
父节点
当前提交
0d5786038a

+ 1 - 1
examples/jsm/materials/LDrawConditionalLineNodeMaterial.js

@@ -50,7 +50,7 @@ class LDrawConditionalLineMaterial extends NodeMaterial {
 
 			varyingProperty( 'float', 'discardFlag' ).assign( discardFlag );
 
-			return modelViewProjection();
+			return modelViewProjection;
 
 		} )();
 

+ 1 - 1
examples/jsm/objects/SkyMesh.js

@@ -98,7 +98,7 @@ class SkyMesh extends Mesh {
 
 			// position
 
-			const position = modelViewProjection();
+			const position = modelViewProjection;
 			position.z.assign( position.w ); // set z to camera.far
 
 			return position;

+ 3 - 3
examples/jsm/tsl/display/SMAANode.js

@@ -178,7 +178,7 @@ class SMAANode extends TempNode {
 			varyingProperty( 'vec4', 'vOffset1' ).assign( vOffset1 );
 			varyingProperty( 'vec4', 'vOffset2' ).assign( vOffset2 );
 
-			return modelViewProjection();
+			return modelViewProjection;
 
 		} );
 
@@ -405,7 +405,7 @@ class SMAANode extends TempNode {
 			varyingProperty( 'vec4', 'vOffset1' ).assign( vOffset1 );
 			varyingProperty( 'vec4', 'vOffset2' ).assign( vOffset2 );
 
-			return modelViewProjection();
+			return modelViewProjection;
 
 		} );
 
@@ -507,7 +507,7 @@ class SMAANode extends TempNode {
 			//varyingProperty( 'vec4', 'vOffset0' ).assign( vOffset0 );
 			varyingProperty( 'vec4', 'vOffset1' ).assign( vOffset1 );
 
-			return modelViewProjection();
+			return modelViewProjection;
 
 		} );
 

二进制
examples/screenshots/webgpu_instance_sprites.jpg


二进制
examples/screenshots/webgpu_tsl_galaxy.jpg


+ 3 - 2
src/Three.TSL.js

@@ -183,8 +183,8 @@ export const grayscale = TSL.grayscale;
 export const greaterThan = TSL.greaterThan;
 export const greaterThanEqual = TSL.greaterThanEqual;
 export const hash = TSL.hash;
-export const highPrecisionModelNormalViewMatrix = TSL.highPrecisionModelNormalViewMatrix;
-export const highPrecisionModelViewMatrix = TSL.highPrecisionModelViewMatrix;
+export const highpModelNormalViewMatrix = TSL.highpModelNormalViewMatrix;
+export const highpModelViewMatrix = TSL.highpModelViewMatrix;
 export const hue = TSL.hue;
 export const instance = TSL.instance;
 export const instanceIndex = TSL.instanceIndex;
@@ -223,6 +223,7 @@ export const log2 = TSL.log2;
 export const logarithmicDepthToViewZ = TSL.logarithmicDepthToViewZ;
 export const loop = TSL.loop;
 export const luminance = TSL.luminance;
+export const mediumpModelViewMatrix = TSL.mediumpModelViewMatrix;
 export const mat2 = TSL.mat2;
 export const mat3 = TSL.mat3;
 export const mat4 = TSL.mat4;

+ 23 - 11
src/materials/nodes/NodeMaterial.js

@@ -23,6 +23,7 @@ import { cameraFar, cameraNear } from '../../nodes/accessors/Camera.js';
 import { clipping, clippingAlpha, hardwareClipping } from '../../nodes/accessors/ClippingNode.js';
 import NodeMaterialObserver from './manager/NodeMaterialObserver.js';
 import getAlphaHashThreshold from '../../nodes/functions/material/getAlphaHashThreshold.js';
+import { modelViewMatrix } from '../../nodes/accessors/ModelNode.js';
 
 class NodeMaterial extends Material {
 
@@ -100,6 +101,7 @@ class NodeMaterial extends Material {
 	setup( builder ) {
 
 		builder.context.setupNormal = () => this.setupNormal( builder );
+		builder.context.setupPositionView = () => this.setupPositionView( builder );
 
 		const renderer = builder.renderer;
 		const renderTarget = renderer.getRenderTarget();
@@ -108,7 +110,9 @@ class NodeMaterial extends Material {
 
 		builder.addStack();
 
-		builder.stack.outputNode = this.vertexNode || this.setupPosition( builder );
+		const vertexNode = this.vertexNode || this.setupVertex( builder );
+
+		builder.stack.outputNode = vertexNode;
 
 		this.setupHardwareClipping( builder );
 
@@ -307,14 +311,27 @@ class NodeMaterial extends Material {
 
 	}
 
-	setupPosition( builder ) {
+	setupPositionView() {
+
+		return modelViewMatrix.mul( positionLocal ).xyz;
+
+	}
 
-		const { object } = builder;
-		const geometry = object.geometry;
+	setupVertex( builder ) {
 
 		builder.addStack();
 
-		// Vertex
+		this.setupPosition( builder );
+
+		builder.context.vertex = builder.removeStack();
+
+		return modelViewProjection;
+
+	}
+
+	setupPosition( builder ) {
+
+		const { object, geometry } = builder;
 
 		if ( geometry.morphAttributes.position || geometry.morphAttributes.normal || geometry.morphAttributes.color ) {
 
@@ -356,12 +373,7 @@ class NodeMaterial extends Material {
 
 		}
 
-		const mvp = modelViewProjection();
-
-		builder.context.vertex = builder.removeStack();
-		builder.context.mvp = mvp;
-
-		return mvp;
+		return positionLocal;
 
 	}
 

+ 9 - 15
src/materials/nodes/SpriteNodeMaterial.js

@@ -2,9 +2,9 @@ import NodeMaterial from './NodeMaterial.js';
 import { cameraProjectionMatrix } from '../../nodes/accessors/Camera.js';
 import { materialRotation } from '../../nodes/accessors/MaterialNode.js';
 import { modelViewMatrix, modelWorldMatrix } from '../../nodes/accessors/ModelNode.js';
-import { positionLocal } from '../../nodes/accessors/Position.js';
+import { positionGeometry, positionLocal } from '../../nodes/accessors/Position.js';
 import { rotate } from '../../nodes/utils/RotateNode.js';
-import { float, vec2, vec3, vec4 } from '../../nodes/tsl/TSLBase.js';
+import { float, vec2, vec4 } from '../../nodes/tsl/TSLBase.js';
 
 import { SpriteMaterial } from '../SpriteMaterial.js';
 import { reference } from '../../nodes/accessors/ReferenceBaseNode.js';
@@ -38,17 +38,17 @@ class SpriteNodeMaterial extends NodeMaterial {
 
 	}
 
-	setupPosition( { object, camera, context } ) {
+	setupPositionView( builder ) {
+
+		const { object, camera } = builder;
 
 		const sizeAttenuation = this.sizeAttenuation;
 
 		// < VERTEX STAGE >
 
-		const { positionNode, rotationNode, scaleNode } = this;
-
-		const vertex = positionLocal;
+		const { rotationNode, scaleNode } = this;
 
-		let mvPosition = modelViewMatrix.mul( vec3( positionNode || 0 ) );
+		const mvPosition = modelViewMatrix.mul( positionLocal );
 
 		let scale = vec2( modelWorldMatrix[ 0 ].xyz.length(), modelWorldMatrix[ 1 ].xyz.length() );
 
@@ -74,7 +74,7 @@ class SpriteNodeMaterial extends NodeMaterial {
 
 		}
 
-		let alignedPosition = vertex.xy;
+		let alignedPosition = positionGeometry.xy;
 
 		if ( object.center && object.center.isVector2 === true ) {
 
@@ -90,13 +90,7 @@ class SpriteNodeMaterial extends NodeMaterial {
 
 		const rotatedPosition = rotate( alignedPosition, rotation );
 
-		mvPosition = vec4( mvPosition.xy.add( rotatedPosition ), mvPosition.zw );
-
-		const modelViewProjection = cameraProjectionMatrix.mul( mvPosition );
-
-		context.vertex = vertex;
-
-		return modelViewProjection;
+		return vec4( mvPosition.xy.add( rotatedPosition ), mvPosition.zw );
 
 	}
 

+ 0 - 1
src/nodes/Nodes.js

@@ -67,7 +67,6 @@ export { default as MaterialReferenceNode } from './accessors/MaterialReferenceN
 export { default as RendererReferenceNode } from './accessors/RendererReferenceNode.js';
 export { default as MorphNode } from './accessors/MorphNode.js';
 export { default as ModelNode } from './accessors/ModelNode.js';
-export { default as ModelViewProjectionNode } from './accessors/ModelViewProjectionNode.js';
 export { default as Object3DNode } from './accessors/Object3DNode.js';
 export { default as PointUVNode } from './accessors/PointUVNode.js';
 export { default as ReferenceNode } from './accessors/ReferenceNode.js';

+ 16 - 5
src/nodes/accessors/ModelNode.js

@@ -39,9 +39,20 @@ export const modelScale = /*@__PURE__*/ nodeImmutable( ModelNode, ModelNode.SCAL
 export const modelViewPosition = /*@__PURE__*/ nodeImmutable( ModelNode, ModelNode.VIEW_POSITION );
 export const modelNormalMatrix = /*@__PURE__*/ uniform( new Matrix3() ).onObjectUpdate( ( { object }, self ) => self.value.getNormalMatrix( object.matrixWorld ) );
 export const modelWorldMatrixInverse = /*@__PURE__*/ uniform( new Matrix4() ).onObjectUpdate( ( { object }, self ) => self.value.copy( object.matrixWorld ).invert() );
-export const modelViewMatrix = /*@__PURE__*/ cameraViewMatrix.mul( modelWorldMatrix ).toVar( 'modelViewMatrix' );
 
-export const highPrecisionModelViewMatrix = /*@__PURE__*/ ( Fn( ( builder ) => {
+export const modelViewMatrix = /*@__PURE__*/ ( Fn( ( builder ) => {
+
+	return builder.renderer.nodes.modelViewMatrix || mediumpModelViewMatrix;
+
+} ).once() )().toVar( 'modelViewMatrix' );
+
+// GPU Precision
+
+export const mediumpModelViewMatrix = /*@__PURE__*/ cameraViewMatrix.mul( modelWorldMatrix );
+
+// CPU Precision
+
+export const highpModelViewMatrix = /*@__PURE__*/ ( Fn( ( builder ) => {
 
 	builder.context.isHighPrecisionModelViewMatrix = true;
 
@@ -51,9 +62,9 @@ export const highPrecisionModelViewMatrix = /*@__PURE__*/ ( Fn( ( builder ) => {
 
 	} );
 
-} ).once() )().toVar( 'highPrecisionModelViewMatrix' );
+} ).once() )().toVar( 'highpModelViewMatrix' );
 
-export const highPrecisionModelNormalViewMatrix = /*@__PURE__*/ ( Fn( ( builder ) => {
+export const highpModelNormalViewMatrix = /*@__PURE__*/ ( Fn( ( builder ) => {
 
 	const isHighPrecisionModelViewMatrix = builder.context.isHighPrecisionModelViewMatrix;
 
@@ -69,4 +80,4 @@ export const highPrecisionModelNormalViewMatrix = /*@__PURE__*/ ( Fn( ( builder
 
 	} );
 
-} ).once() )().toVar( 'highPrecisionModelNormalMatrix' );
+} ).once() )().toVar( 'highpModelNormalViewMatrix' );

+ 2 - 40
src/nodes/accessors/ModelViewProjectionNode.js

@@ -1,42 +1,4 @@
-import TempNode from '../core/TempNode.js';
 import { cameraProjectionMatrix } from './Camera.js';
-import { positionLocal } from './Position.js';
-import { nodeProxy, varying } from '../tsl/TSLBase.js';
-import { modelViewMatrix } from './ModelNode.js';
+import { positionView } from './Position.js';
 
-class ModelViewProjectionNode extends TempNode {
-
-	static get type() {
-
-		return 'ModelViewProjectionNode';
-
-	}
-
-	constructor( positionNode = null ) {
-
-		super( 'vec4' );
-
-		this.positionNode = positionNode;
-
-	}
-
-	setup( builder ) {
-
-		if ( builder.shaderStage === 'fragment' ) {
-
-			return varying( builder.context.mvp );
-
-		}
-
-		const position = this.positionNode || positionLocal;
-		const viewMatrix = builder.renderer.nodes.modelViewMatrix || modelViewMatrix;
-
-		return cameraProjectionMatrix.mul( viewMatrix ).mul( position );
-
-	}
-
-}
-
-export default ModelViewProjectionNode;
-
-export const modelViewProjection = /*@__PURE__*/ nodeProxy( ModelViewProjectionNode );
+export const modelViewProjection = /*@__PURE__*/ cameraProjectionMatrix.mul( positionView ).varying( 'v_modelViewProjection' );

+ 7 - 2
src/nodes/accessors/Position.js

@@ -1,5 +1,6 @@
 import { attribute } from '../core/AttributeNode.js';
-import { modelWorldMatrix, modelViewMatrix } from './ModelNode.js';
+import { Fn } from '../tsl/TSLCore.js';
+import { modelWorldMatrix } from './ModelNode.js';
 
 /** @module Position **/
 
@@ -44,7 +45,11 @@ export const positionWorldDirection = /*@__PURE__*/ positionLocal.transformDirec
  *
  * @type {VaryingNode<vec3>}
  */
-export const positionView = /*@__PURE__*/ modelViewMatrix.mul( positionLocal ).xyz.varying( 'v_positionView' ).context( { needsPositionReassign: true } );
+export const positionView = /*@__PURE__*/ ( Fn( ( builder ) => {
+
+	return builder.context.setupPositionView();
+
+}, 'vec3' ).once() )().varying( 'v_positionView' ).context( { needsPositionReassign: true } );
 
 /**
  * TSL object that represents the position view direction of the current rendered object.

+ 1 - 1
src/renderers/common/Background.js

@@ -60,7 +60,7 @@ class Background extends DataMap {
 					getTextureLevel: () => backgroundBlurriness
 				} );
 
-				let viewProj = modelViewProjection();
+				let viewProj = modelViewProjection;
 				viewProj = viewProj.setZ( viewProj.w );
 
 				const nodeMaterial = new NodeMaterial();

粤ICP备19079148号