Skip to content

⬅️ Back to Table of Contents

📄 AssignNode.js

📊 Analysis Summary

Metric Count
🔧 Functions 5
🧱 Classes 1
📦 Imports 4
📊 Variables & Constants 4

📚 Table of Contents

🛠️ File Location:

📂 src/nodes/core/AssignNode.js

📦 Imports

Name Source
TempNode ../core/TempNode.js
addMethodChaining ../tsl/TSLCore.js
nodeProxy ../tsl/TSLCore.js
vectorComponents ../core/constants.js

Variables & Constants

Name Type Kind Value Exported
assignDifferentVector boolean let/var vectorComponents.join( '' ).slice( 0, targetLength ) !== targetNode.components
snippet any let/var *not shown*
splitNode any let/var targetNode.node
component any let/var splitNode.components[ i ]

Functions

AssignNode.hasDependencies(): boolean

JSDoc:

/**
     * Whether this node is used more than once in context of other nodes. This method
     * is overwritten since it always returns `false` (assigns are unique).
     *
     * @return {boolean} A flag that indicates if there is more than one dependency to other nodes. Always `false`.
     */

Returns: boolean

Code
hasDependencies() {

        return false;

    }

AssignNode.getNodeType(builder: any, output: any): any

Parameters:

  • builder any
  • output any

Returns: any

Calls:

  • this.targetNode.getNodeType
Code
getNodeType( builder, output ) {

        return output !== 'void' ? this.targetNode.getNodeType( builder ) : 'void';

    }

AssignNode.needsSplitAssign(builder: NodeBuilder): boolean

JSDoc:

/**
     * Whether a split is required when assigning source to target. This can happen when the component length of
     * target and source data type does not match.
     *
     * @param {NodeBuilder} builder - The current node builder.
     * @return {boolean} Whether a split is required when assigning source to target.
     */

Parameters:

  • builder NodeBuilder

Returns: boolean

Calls:

  • builder.isAvailable
  • builder.getTypeLength
  • targetNode.node.getNodeType
  • vectorComponents.join( '' ).slice
Code
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 assignDifferentVector = vectorComponents.join( '' ).slice( 0, targetLength ) !== targetNode.components;

            return assignDifferentVector;

        }

        return false;

    }

AssignNode.setup(builder: any): void

Parameters:

  • builder any

Returns: void

Calls:

  • builder.getNodeProperties
  • targetNode.context
Code
setup( builder ) {

        const { targetNode, sourceNode } = this;

        const targetProperties = builder.getNodeProperties( targetNode );
        targetProperties.assign = true;

        const properties = builder.getNodeProperties( this );
        properties.sourceNode = sourceNode;
        properties.targetNode = targetNode.context( { assign: true } );

    }

AssignNode.generate(builder: any, output: any): any

Parameters:

  • builder any
  • output any

Returns: any

Calls:

  • builder.getNodeProperties
  • this.needsSplitAssign
  • targetNode.build
  • targetNode.getNodeType
  • sourceNode.build
  • sourceNode.getNodeType
  • builder.getDataFromNode
  • builder.getVarFromNode
  • builder.getPropertyName
  • builder.addLineFlowCode
  • splitNode.node.context
  • splitTargetNode.build
  • builder.format

Internal Comments:

// (x2)

Code
generate( builder, output ) {

        const { targetNode, sourceNode } = builder.getNodeProperties( this );

        const needsSplitAssign = this.needsSplitAssign( builder );

        const target = targetNode.build( builder );
        const targetType = targetNode.getNodeType( 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 }`, this );

            const splitNode = targetNode.node;
            const splitTargetNode = splitNode.node.context( { assign: true } );

            const targetRoot = splitTargetNode.build( builder );

            for ( let i = 0; i < splitNode.components.length; i ++ ) {

                const component = splitNode.components[ i ];

                builder.addLineFlowCode( `${ targetRoot }.${ component } = ${ sourceProperty }[ ${ i } ]`, this );

            }

            if ( output !== 'void' ) {

                snippet = target;

            }

        } else {

            snippet = `${ target } = ${ source }`;

            if ( output === 'void' || sourceType === 'void' ) {

                builder.addLineFlowCode( snippet, this );

                if ( output !== 'void' ) {

                    snippet = target;

                }

            }

        }

        nodeData.initialized = true;

        return builder.format( snippet, targetType, output );

    }

Classes

AssignNode

Class Code
class AssignNode extends TempNode {

    static get type() {

        return 'AssignNode';

    }

    /**
     * Constructs a new assign node.
     *
     * @param {Node} targetNode - The target node.
     * @param {Node} sourceNode - The source type.
     */
    constructor( targetNode, sourceNode ) {

        super();

        /**
         * The target node.
         *
         * @type {Node}
         */
        this.targetNode = targetNode;

        /**
         * The source node.
         *
         * @type {Node}
         */
        this.sourceNode = sourceNode;

        /**
         * This flag can be used for type testing.
         *
         * @type {boolean}
         * @readonly
         * @default true
         */
        this.isAssignNode = true;

    }

    /**
     * Whether this node is used more than once in context of other nodes. This method
     * is overwritten since it always returns `false` (assigns are unique).
     *
     * @return {boolean} A flag that indicates if there is more than one dependency to other nodes. Always `false`.
     */
    hasDependencies() {

        return false;

    }

    getNodeType( builder, output ) {

        return output !== 'void' ? this.targetNode.getNodeType( builder ) : 'void';

    }

    /**
     * Whether a split is required when assigning source to target. This can happen when the component length of
     * target and source data type does not match.
     *
     * @param {NodeBuilder} builder - The current node builder.
     * @return {boolean} Whether a split is required when assigning source to target.
     */
    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 assignDifferentVector = vectorComponents.join( '' ).slice( 0, targetLength ) !== targetNode.components;

            return assignDifferentVector;

        }

        return false;

    }

    setup( builder ) {

        const { targetNode, sourceNode } = this;

        const targetProperties = builder.getNodeProperties( targetNode );
        targetProperties.assign = true;

        const properties = builder.getNodeProperties( this );
        properties.sourceNode = sourceNode;
        properties.targetNode = targetNode.context( { assign: true } );

    }

    generate( builder, output ) {

        const { targetNode, sourceNode } = builder.getNodeProperties( this );

        const needsSplitAssign = this.needsSplitAssign( builder );

        const target = targetNode.build( builder );
        const targetType = targetNode.getNodeType( 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 }`, this );

            const splitNode = targetNode.node;
            const splitTargetNode = splitNode.node.context( { assign: true } );

            const targetRoot = splitTargetNode.build( builder );

            for ( let i = 0; i < splitNode.components.length; i ++ ) {

                const component = splitNode.components[ i ];

                builder.addLineFlowCode( `${ targetRoot }.${ component } = ${ sourceProperty }[ ${ i } ]`, this );

            }

            if ( output !== 'void' ) {

                snippet = target;

            }

        } else {

            snippet = `${ target } = ${ source }`;

            if ( output === 'void' || sourceType === 'void' ) {

                builder.addLineFlowCode( snippet, this );

                if ( output !== 'void' ) {

                    snippet = target;

                }

            }

        }

        nodeData.initialized = true;

        return builder.format( snippet, targetType, output );

    }

}

Methods

hasDependencies(): boolean
Code
hasDependencies() {

        return false;

    }
getNodeType(builder: any, output: any): any
Code
getNodeType( builder, output ) {

        return output !== 'void' ? this.targetNode.getNodeType( builder ) : 'void';

    }
needsSplitAssign(builder: NodeBuilder): boolean
Code
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 assignDifferentVector = vectorComponents.join( '' ).slice( 0, targetLength ) !== targetNode.components;

            return assignDifferentVector;

        }

        return false;

    }
setup(builder: any): void
Code
setup( builder ) {

        const { targetNode, sourceNode } = this;

        const targetProperties = builder.getNodeProperties( targetNode );
        targetProperties.assign = true;

        const properties = builder.getNodeProperties( this );
        properties.sourceNode = sourceNode;
        properties.targetNode = targetNode.context( { assign: true } );

    }
generate(builder: any, output: any): any
Code
generate( builder, output ) {

        const { targetNode, sourceNode } = builder.getNodeProperties( this );

        const needsSplitAssign = this.needsSplitAssign( builder );

        const target = targetNode.build( builder );
        const targetType = targetNode.getNodeType( 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 }`, this );

            const splitNode = targetNode.node;
            const splitTargetNode = splitNode.node.context( { assign: true } );

            const targetRoot = splitTargetNode.build( builder );

            for ( let i = 0; i < splitNode.components.length; i ++ ) {

                const component = splitNode.components[ i ];

                builder.addLineFlowCode( `${ targetRoot }.${ component } = ${ sourceProperty }[ ${ i } ]`, this );

            }

            if ( output !== 'void' ) {

                snippet = target;

            }

        } else {

            snippet = `${ target } = ${ source }`;

            if ( output === 'void' || sourceType === 'void' ) {

                builder.addLineFlowCode( snippet, this );

                if ( output !== 'void' ) {

                    snippet = target;

                }

            }

        }

        nodeData.initialized = true;

        return builder.format( snippet, targetType, output );

    }