def create(cls, enclosingNode, locationPath):
        """
        Creates the contents of the EditStackNode that contains the edit nodes.
        This could be any other kind of node with at least one input and one
        output, but the createPackageEditStackNode() helper function does all
        of the configuration boilerplate code of an EditStackNode for you.
        The return value is a ArnoldSpotLightGafferEditPackage instance.

        This particular package node will contain a TransformEdit node on it,
        which will allow to edit the transform of a spot light.
        """
        # Create the package node. Since this is an edit package we want to use
        # an EditStackNode instead of a GroupNode, since it already has an
        # input and an output by default. This also adds some necessary
        # parameters to this node.
        packageNode = cls.createPackageEditStackNode(enclosingNode,
                                                     locationPath)

        # Build material edit node
        materialNode = NodegraphAPI.CreateNode('Material', packageNode)
        actionParam = materialNode.getParameter('action')
        actionParam.setValue('edit material', 0)

        editLocationParam = materialNode.getParameter('edit.location')
        editLocationParam.setExpression('=^/__gaffer.location')
        editLocationParam.setExpressionFlag(True)
        NU.AddNodeRef(packageNode, 'material_edit', materialNode)

        packageNode.buildChildNode(adoptNode=materialNode)

        # Build transform edit node
        transformEditNode = NodegraphAPI.CreateNode('TransformEdit',
                                                    packageNode)
        actionParam = transformEditNode.getParameter('action')
        actionParam.setValue('override interactive transform', 0)

        pathParam = transformEditNode.getParameter('path')
        pathParam.setExpression('=^/__gaffer.location')
        pathParam.setExpressionFlag(True)

        # Adds reference parameters to the transform edit node
        NU.AddNodeRef(packageNode, 'transform_edit', transformEditNode)

        # Add the transform edit node into the package node using
        # EditStackNode's buildChildNode().
        packageNode.buildChildNode(adoptNode=transformEditNode)

        # Create and append light linking nodes
        linkingNodes = Packages.LinkingMixin.getLinkingNodes(packageNode,
                                                             create=True)
        NU.AppendNodes(
            packageNode,
            tuple(linkingNode for linkingNode in linkingNodes
                  if linkingNode is not None))

        # Instantiate a package with the package node
        return cls.createPackage(packageNode)
Esempio n. 2
0
    def create(cls, enclosingNode, locationPath):
        """
        A factory method which returns an instance of the class.

        @type enclosingNode: C{NodegraphAPI.Node}
        @type locationPath: C{str}
        @rtype: L{LightPackage}
        @param enclosingNode: The parent node within which the new
            package's node should be created.
        @param locationPath: The path to the location to be created/managed
            by the package.
        @return: The newly-created package instance.
        """
        # Create the package node
        packageNode = NodegraphAPI.CreateNode('Group', enclosingNode)
        packageNode.addOutputPort('out')

        # Add parameter containing the package type and location path to the
        # package node
        NU.AddPackageTypeAndPath(packageNode, cls.__name__, locationPath)

        # Create an expression to link the name of the sky dome location to the
        # name of the package.
        locExpr = '=^/%s' % NU.GetPackageLocationParameterPath()

        # Create geometry for the light - in this case a sphere
        createNode = NodegraphAPI.CreateNode('PrimitiveCreate', packageNode)
        createNode.getParameter('type').setValue('coordinate system sphere', 0)
        createNode.getParameter('transform.scale.x').setValue(
            cls.DEFAULT_SIZE, 0)
        scaleExpr = "=transform.scale.x"
        createNode.getParameter('transform.scale.y').setExpression(scaleExpr)
        createNode.getParameter('transform.scale.z').setExpression(scaleExpr)
        createNode.getParameters().createChildNumber('forceAsStaticScene', 1)

        createNodeExtraAttrsParameter = \
            createNode.getParameters().createChildGroup('extraAttrs')
        createNodeExtraAttrsParameter.createChildString(
            '__gafferPackage', '').setExpression('@%s' % packageNode.getName())
        createNode.getParameter('name').setExpression(locExpr)
        createNode.addInputPort('masterMaterial')

        # Store the package class as a parameter on the create node
        NU.SetOrCreateDeepScalarParameter(
            createNode.getParameters(), 'extraAttrs.info.gaffer.packageClass',
            cls.__name__)

        # Set the type of the package location to "light", so that the Gaffer
        # recognizes it as such
        typeAttrSetNode = NodegraphAPI.CreateNode('AttributeSet', packageNode)
        typeAttrSetNode.setName("SetTypeAttributeSet")
        typeAttrSetNode.getParameter('paths.i0').setExpression(locExpr)
        typeAttrSetNode.getParameter('attributeName').setValue('type', 0)
        typeAttrSetNode.getParameter('attributeType').setValue('string', 0)
        typeAttrSetNode.getParameter('stringValue.i0').setValue('light', 0)

        # Set the "viewer.locationType" attribute on the package location to
        # "nurbspatch", so that the viewer knows to display it as geometry
        viewerTypeAttrSetNode = NodegraphAPI.CreateNode(
            'AttributeSet', packageNode)
        viewerTypeAttrSetNode.setName("SetViewerTypeAttributeSet")
        viewerTypeAttrSetNode.getParameter('paths.i0').setExpression(locExpr)
        viewerTypeAttrSetNode.getParameter('attributeName').setValue(
            'viewer.locationType', 0)
        viewerTypeAttrSetNode.getParameter('attributeType').setValue(
            'string', 0)
        viewerTypeAttrSetNode.getParameter('stringValue.i0').setValue(
            'nurbspatch', 0)

        # Add the package location to the light list at /root
        lightListEditNode = NodegraphAPI.CreateNode('LightListEdit',
                                                    packageNode)
        lightListEditNode.setName("LightListEdit")
        lightListEditNode.getParameter('locations.i0').setExpression(locExpr)

        # Create the Material node
        materialNode = NodegraphAPI.CreateNode('Material', packageNode)
        materialNode.getParameter('action').setValue('edit material', 0)
        materialNode.getParameter('makeInteractive').setValue('Yes', 0)
        materialNode.getParameters().createChildNumber(
            'makeInteractiveSpecificToMaterial', 1)
        materialNode.getParameter('edit.location').setExpression(locExpr)

        # Create an OpScript node to copy the preview texture from the shader
        # to the sphere
        copyPreviewTextureOpScriptNode = cls.__createOpScriptNode(
            packageNode, 'CopyPreviewTextureOpScript',
            cls.__getPreviewTextureOpScript())

        # Create an OpScript node to copy the transform from the sphere to the
        # shader
        copyXformOpScriptNode = cls.__createOpScriptNode(
            packageNode, 'CopyXformOpScript', cls.__getCopyXformOpScript())

        # Create an OpScript node to flip the UVs in the viewer
        viewerUVFlipOpScriptNode = cls.__createOpScriptNode(
            packageNode, 'ViewerUVFlipOpScript',
            cls.__getViewerUVFlipOpScript())

        # Create a DistantPort node to reference the master material
        masterMaterialDistantPortNode = NodegraphAPI.CreateNode(
            'DistantPort', packageNode)
        masterMaterialDistantPortNode.setBypassed(True)

        # Create a ViewerObjectSettings node in case we want to customize how
        # the skydome is displayed in the viewer
        viewerObjectSettingsNode = NodegraphAPI.CreateNode(
            'ViewerObjectSettings', packageNode)
        viewerObjectSettingsNode.getParameter('CEL').setExpression(locExpr)

        # Add node references to the package node
        NU.AddNodeRef(packageNode, 'create', createNode)
        NU.AddNodeRef(packageNode, 'lightListEdit', lightListEditNode)
        NU.AddNodeRef(packageNode, 'material', materialNode)
        NU.AddNodeRef(packageNode, 'master', masterMaterialDistantPortNode)
        NU.AddNodeRef(packageNode, 'viewerObjectSettings',
                      viewerObjectSettingsNode)

        # Wire up and position the nodes
        NU.WireInlineNodes(
            packageNode,
            (masterMaterialDistantPortNode, createNode, typeAttrSetNode,
             viewerTypeAttrSetNode, lightListEditNode, materialNode,
             copyPreviewTextureOpScriptNode, copyXformOpScriptNode,
             viewerUVFlipOpScriptNode, viewerObjectSettingsNode))

        # Create and append light linking nodes
        linkingNodes = Packages.LinkingMixin.getLinkingNodes(packageNode,
                                                             create=True)
        NU.AppendNodes(
            packageNode,
            tuple(linkingNode for linkingNode in linkingNodes
                  if linkingNode is not None))
        # Create a package node instance
        result = cls(packageNode)
        Packages.CallbackMixin.executeCreationCallback(result)

        # Create a post-merge stack node for this package
        postMergeNode = result.createPostMergeStackNode()

        # Use an AttributeSet node to set Arnold's background attribute at root
        arnoldBGAttrSetNode = NodegraphAPI.CreateNode('AttributeSet',
                                                      packageNode)
        arnoldBGAttrSetNode.setName("ArnoldBGAttributeSet")
        arnoldBGAttrSetNode.getParameter('paths.i0').setValue('/root', 0)
        arnoldBGAttrSetNode.getParameter('attributeName').setValue(
            'arnoldGlobalStatements.background', 0)
        arnoldBGAttrSetNode.getParameter('attributeType').setValue('string', 0)
        arnoldBGAttrSetNode.getParameter('stringValue.i0').setExpression(
            'getParam("%s.__gaffer.location")' % packageNode.getName())
        postMergeNode.buildChildNode(adoptNode=arnoldBGAttrSetNode)

        # Set our material to point at a baked Look File material
        result.setLookFileMaterial(
            cls.DEFAULT_BAKED_LIGHT_FILENAME,
            "/root/materials/%s" % cls.DEFAULT_BAKED_LIGHT_NAME)

        return result
Esempio n. 3
0
    def create(cls, enclosingNode, locationPath, shaderName=''):
        """
        A factory method which returns an instance of the class.

        @type enclosingNode: C{NodegraphAPI.Node}
        @type locationPath: C{str}
        @rtype: L{LightPackage}
        @param enclosingNode: The parent node within which the new
            package's node should be created.
        @param locationPath: The path to the location to be created/managed
            by the package.
        @return: The newly-created package instance.
        """
        # Create the package node
        packageNode = NodegraphAPI.CreateNode('Group', enclosingNode)
        packageNode.addOutputPort('out')

        # Add parameter containing the package type and location path to the package node
        NU.AddPackageTypeAndPath(packageNode, cls.__name__, locationPath)

        # Create an expression to link the name of the sky dome location to the name of the package
        locExpr = '=^/%s' % NU.GetPackageLocationParameterPath()

        # Create geometry for the light - in this case a bounded plane
        createNode = NodegraphAPI.CreateNode('LightCreate', packageNode)
        createNode.getParameter('transform.scale.x').setValue(cls.DEFAULT_SIZE, 0)
        scaleExpr = "=transform.scale.x"
        createNode.getParameter('transform.scale.y').setExpression(scaleExpr)
        createNode.getParameter('transform.scale.z').setExpression(scaleExpr)
        createNode.getParameters().createChildNumber('forceAsStaticScene', 1)

        createNodeExtraAttrsParameter = createNode.getParameters().createChildGroup('extraAttrs')
        createNodeExtraAttrsParameter.createChildString('__gafferPackage', '').setExpression('@%s' % packageNode.getName())
        createNode.getParameter('name').setExpression(locExpr)
        createNode.addInputPort('masterMaterial')

        # Store the package class as a parameter on the create node
        NU.SetOrCreateDeepScalarParameter(createNode.getParameters(),
                                          'extraAttrs.info.gaffer.packageClass',
                                          cls.__name__)

        # Add the package location to the light list at /root
        lightListEditNode = NodegraphAPI.CreateNode('LightListEdit', packageNode)
        lightListEditNode.setName("LightListEdit")
        lightListEditNode.getParameter('locations.i0').setExpression(locExpr)

        # Create the Material node
        materialNode = NodegraphAPI.CreateNode('Material', packageNode)
        materialNode.getParameter('action').setValue('edit material', 0)
        materialNode.getParameter('makeInteractive').setValue('Yes', 0)
        materialNode.getParameters().createChildNumber('makeInteractiveSpecificToMaterial', 1)
        materialNode.getParameter('edit.location').setExpression(locExpr)

        # Create an OpScript node to copy the transform from the sphere to the shader
        copyXformOpScriptNode = cls.createOpScriptNode(packageNode,
                                                         'CopyXformOpScript',
                                                         cls.getCopyXformOpScript())

        # Create a DistantPort node to reference the master material
        masterMaterialDistantPortNode = NodegraphAPI.CreateNode('DistantPort', packageNode)
        masterMaterialDistantPortNode.setBypassed(True)

        # Create a ViewerObjectSettings node in case we want to customize how
        # the spot light is displayed in the viewer
        viewerObjectSettingsNode = NodegraphAPI.CreateNode('ViewerObjectSettings', packageNode)
        viewerObjectSettingsNode.getParameter('CEL').setExpression(locExpr)

        # Create the Merge node, for merging in child packages
        mergeNode = NodegraphAPI.CreateNode('Merge', packageNode)
        mergeNode.addInputPort('i0')

        # Add node references to the package node
        NU.AddNodeRef(packageNode, 'create', createNode)
        NU.AddNodeRef(packageNode, 'lightListEdit', lightListEditNode)
        NU.AddNodeRef(packageNode, 'material', materialNode)
        NU.AddNodeRef(packageNode, 'master', masterMaterialDistantPortNode)
        NU.AddNodeRef(packageNode, 'viewerObjectSettings', viewerObjectSettingsNode)
        NU.AddNodeRef(packageNode, 'merge', mergeNode)

        # Wire up and position the nodes
        NU.WireInlineNodes(packageNode, (masterMaterialDistantPortNode,
                                         createNode,
                                         lightListEditNode,
                                         materialNode,
                                         copyXformOpScriptNode,
                                         viewerObjectSettingsNode,
                                         mergeNode))

        # Create and append light linking nodes
        linkingNodes = Packages.LinkingMixin.getLinkingNodes(packageNode, create=True)
        NU.AppendNodes(packageNode, tuple(linkingNode for linkingNode in linkingNodes if linkingNode is not None))

        # Create a package node instance
        result = cls(packageNode)
        Packages.CallbackMixin.executeCreationCallback(result)

        # By default we use inline shaders, rather than forcing the user through look files, so this is old:
        # Set our material to point at a baked Look File material
        #result.setLookFileMaterial(cls.DEFAULT_BAKED_LIGHT_FILENAME, "/root/materials/%s" % cls.DEFAULT_BAKED_LIGHT_NAME)

        # Set the main shader
        result.setShader('arnoldLight', shaderName)

        return result