Skip to content

Commit 4b2ff23

Browse files
committed
Reapply "TSL: Forces assignment of a function call if a loop is detected (mrdoob#31961)" (mrdoob#31975)
This reverts commit 699e1fa.
1 parent 42d5bed commit 4b2ff23

File tree

6 files changed

+86
-30
lines changed

6 files changed

+86
-30
lines changed

src/nodes/core/ContextNode.js

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -94,9 +94,7 @@ class ContextNode extends Node {
9494

9595
analyze( builder ) {
9696

97-
const previousContext = builder.getContext();
98-
99-
builder.setContext( { ...builder.context, ...this.value } );
97+
const previousContext = builder.addContext( this.value );
10098

10199
this.node.build( builder );
102100

@@ -106,9 +104,7 @@ class ContextNode extends Node {
106104

107105
setup( builder ) {
108106

109-
const previousContext = builder.getContext();
110-
111-
builder.setContext( { ...builder.context, ...this.value } );
107+
const previousContext = builder.addContext( this.value );
112108

113109
this.node.build( builder );
114110

@@ -118,9 +114,7 @@ class ContextNode extends Node {
118114

119115
generate( builder, output ) {
120116

121-
const previousContext = builder.getContext();
122-
123-
builder.setContext( { ...builder.context, ...this.value } );
117+
const previousContext = builder.addContext( this.value );
124118

125119
const snippet = this.node.build( builder, output );
126120

src/nodes/core/NodeBuilder.js

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -899,6 +899,22 @@ class NodeBuilder {
899899

900900
}
901901

902+
/**
903+
* Adds context data to the builder's current context.
904+
*
905+
* @param {Object} context - The context to add.
906+
* @return {Object} The previous context.
907+
*/
908+
addContext( context ) {
909+
910+
const previousContext = this.getContext();
911+
912+
this.setContext( { ...this.context, ...context } );
913+
914+
return previousContext;
915+
916+
}
917+
902918
/**
903919
* Gets a context used in shader construction that can be shared across different materials.
904920
* This is necessary since the renderer cache can reuse shaders generated in one material and use them in another.

src/nodes/core/StackNode.js

Lines changed: 4 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -261,15 +261,9 @@ class StackNode extends Node {
261261

262262
for ( const childNode of this.getChildren() ) {
263263

264-
if ( childNode.isVarNode && childNode.intent === true ) {
264+
if ( childNode.isVarNode && childNode.isAssign( builder ) !== true ) {
265265

266-
const properties = builder.getNodeProperties( childNode );
267-
268-
if ( properties.assign !== true ) {
269-
270-
continue;
271-
272-
}
266+
continue;
273267

274268
}
275269

@@ -302,15 +296,9 @@ class StackNode extends Node {
302296

303297
for ( const node of this.nodes ) {
304298

305-
if ( node.isVarNode && node.intent === true ) {
299+
if ( node.isVarNode && node.isAssign( builder ) !== true ) {
306300

307-
const properties = builder.getNodeProperties( node );
308-
309-
if ( properties.assign !== true ) {
310-
311-
continue;
312-
313-
}
301+
continue;
314302

315303
}
316304

src/nodes/core/VarNode.js

Lines changed: 41 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -146,14 +146,53 @@ class VarNode extends Node {
146146

147147
}
148148

149+
isAssign( builder ) {
150+
151+
if ( this.intent !== true ) return true;
152+
153+
//
154+
155+
const properties = builder.getNodeProperties( this );
156+
157+
let assign = properties.assign;
158+
159+
if ( assign !== true ) {
160+
161+
if ( this.node.isShaderCallNodeInternal && this.node.shaderNode.getLayout() === null ) {
162+
163+
if ( builder.context.fnCall && builder.context.fnCall.shaderNode ) {
164+
165+
const nodeType = this.node.getNodeType( builder );
166+
167+
if ( nodeType !== 'void' ) {
168+
169+
const shaderNodeData = builder.getDataFromNode( this.node.shaderNode );
170+
171+
if ( shaderNodeData.hasLoop ) {
172+
173+
assign = true;
174+
175+
}
176+
177+
}
178+
179+
}
180+
181+
}
182+
183+
}
184+
185+
return assign;
186+
187+
}
188+
149189
build( ...params ) {
150190

151191
if ( this.intent === true ) {
152192

153193
const builder = params[ 0 ];
154-
const properties = builder.getNodeProperties( this );
155194

156-
if ( properties.assign !== true ) {
195+
if ( this.isAssign( builder ) !== true ) {
157196

158197
return this.node.build( ...params );
159198

src/nodes/tsl/TSLCore.js

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -488,6 +488,7 @@ class ShaderCallNodeInternal extends Node {
488488
//
489489

490490
const previousSubBuildFn = builder.subBuildFn;
491+
const previousContext = builder.addContext( { fnCall: this } );
491492

492493
builder.subBuildFn = subBuild;
493494

@@ -565,6 +566,7 @@ class ShaderCallNodeInternal extends Node {
565566
}
566567

567568
builder.subBuildFn = previousSubBuildFn;
569+
builder.setContext( previousContext );
568570

569571
if ( shaderNode.once ) {
570572

@@ -608,6 +610,8 @@ class ShaderCallNodeInternal extends Node {
608610
const subBuildOutput = builder.getSubBuildOutput( this );
609611
const outputNode = this.getOutputNode( builder );
610612

613+
const previousContext = builder.addContext( { fnCall: this } );
614+
611615
if ( buildStage === 'setup' ) {
612616

613617
const subBuildInitialized = builder.getSubBuildProperty( 'initialized', this );
@@ -655,6 +659,8 @@ class ShaderCallNodeInternal extends Node {
655659

656660
}
657661

662+
builder.setContext( previousContext );
663+
658664
return result;
659665

660666
}
@@ -788,9 +794,15 @@ class ShaderNodeInternal extends Node {
788794

789795
}
790796

797+
getLayout() {
798+
799+
return this.layout;
800+
801+
}
802+
791803
call( rawInputs = null ) {
792804

793-
return nodeObject( new ShaderCallNodeInternal( this, rawInputs ) );
805+
return new ShaderCallNodeInternal( this, rawInputs );
794806

795807
}
796808

src/nodes/utils/LoopNode.js

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import Node from '../core/Node.js';
22
import { expression } from '../code/ExpressionNode.js';
3-
import { nodeObject, nodeArray, Fn } from '../tsl/TSLBase.js';
3+
import { nodeArray, Fn } from '../tsl/TSLBase.js';
44
import { error } from '../../utils.js';
55

66
/**
@@ -139,6 +139,13 @@ class LoopNode extends Node {
139139

140140
this.getProperties( builder );
141141

142+
if ( builder.context.fnCall ) {
143+
144+
const shaderNodeData = builder.getDataFromNode( builder.context.fnCall.shaderNode );
145+
shaderNodeData.hasLoop = true;
146+
147+
}
148+
142149
}
143150

144151
generate( builder ) {
@@ -333,7 +340,7 @@ export default LoopNode;
333340
* @param {...any} params - A list of parameters.
334341
* @returns {LoopNode}
335342
*/
336-
export const Loop = ( ...params ) => nodeObject( new LoopNode( nodeArray( params, 'int' ) ) ).toStack();
343+
export const Loop = ( ...params ) => new LoopNode( nodeArray( params, 'int' ) ).toStack();
337344

338345
/**
339346
* TSL function for creating a `Continue()` expression.

0 commit comments

Comments
 (0)