three
Version:
JavaScript 3D library
129 lines (68 loc) • 2.63 kB
JavaScript
import { addNodeClass } from '../core/Node.js';
import TempNode from '../core/TempNode.js';
import { addNodeElement, nodeProxy } from '../shadernode/ShaderNode.js';
import { vectorComponents } from '../core/constants.js';
class AssignNode extends TempNode {
constructor( targetNode, sourceNode ) {
super();
this.targetNode = targetNode;
this.sourceNode = sourceNode;
}
hasDependencies() {
return false;
}
getNodeType( builder, output ) {
return output !== 'void' ? this.targetNode.getNodeType( builder ) : 'void';
}
needsSplitAssign( builder ) {
const { targetNode } = this;
if ( builder.isAvailable( 'swizzleAssign' ) === false && targetNode.isSplitNode && targetNode.components.length > 1 ) {
const targetLength = builder.getTypeLength( targetNode.node.getNodeType( builder ) );
const assignDiferentVector = vectorComponents.join( '' ).slice( 0, targetLength ) !== targetNode.components;
return assignDiferentVector;
}
return false;
}
generate( builder, output ) {
const { targetNode, sourceNode } = this;
const needsSplitAssign = this.needsSplitAssign( builder );
const targetType = targetNode.getNodeType( builder );
const target = targetNode.context( { assign: true } ).build( builder );
const source = sourceNode.build( builder, targetType );
const sourceType = sourceNode.getNodeType( builder );
const nodeData = builder.getDataFromNode( this );
//
let snippet;
if ( nodeData.initialized === true ) {
if ( output !== 'void' ) {
snippet = target;
}
} else if ( needsSplitAssign ) {
const sourceVar = builder.getVarFromNode( this, null, targetType );
const sourceProperty = builder.getPropertyName( sourceVar );
builder.addLineFlowCode( `${ sourceProperty } = ${ source }` );
const targetRoot = targetNode.node.context( { assign: true } ).build( builder );
for ( let i = 0; i < targetNode.components.length; i ++ ) {
const component = targetNode.components[ i ];
builder.addLineFlowCode( `${ targetRoot }.${ component } = ${ sourceProperty }[ ${ i } ]` );
}
if ( output !== 'void' ) {
snippet = target;
}
} else {
snippet = `${ target } = ${ source }`;
if ( output === 'void' || sourceType === 'void' ) {
builder.addLineFlowCode( snippet );
if ( output !== 'void' ) {
snippet = target;
}
}
}
nodeData.initialized = true;
return builder.format( snippet, targetType, output );
}
}
export default AssignNode;
export const assign = nodeProxy( AssignNode );
addNodeClass( 'AssignNode', AssignNode );
addNodeElement( 'assign', assign );