Create Connection
# The following is an example on how to create connections.
import ufe
import lookdevx as lx
if not shadingContainer:
raise Exception('This example requires a shading container i.e., a MaterialX document or a USD '
'material. Check the other examples to see how to create one.')
# Create some nodes.
runTimeId = shadingContainer.runTimeId()
items = []
for _ in range(3):
items.append(ufe.NodeDef.definition(runTimeId, 'ND_add_float').createNode(shadingContainer, ufe.PathComponent('add')))
# Connections can be created using the `ufe.ConnectionHandler` of the respective UFE runtime. It can
# be fetched from the UFE runtime manager.
connectionHandler = ufe.RunTimeMgr.instance().connectionHandler(runTimeId)
# To connect ports on two nodes, either specify their paths and attribute names in a
# `ufe.AttributeInfo` or use the `ufe.Attributes` interface to fetch `ufe.Attribute` objects.
# Connect using `ufe.AttributeInfo`.
srcInfo = ufe.AttributeInfo(items[0].path(), 'outputs:out')
dstInfo = ufe.AttributeInfo(items[1].path(), 'inputs:in1')
connectionHandler.connect(srcInfo, dstInfo)
# Note that the attribute names are either prefixed with `inputs:` or `outputs:`. UFE uses this
# convention to differentiate input and output ports. Usually connections are `output -> input`, but
# when connecting a port of a node to a port of the node's parent compound, it's possible to have
# `input -> input` and `output -> output` connections, as show further below.
print('Created connection: '
f'{ufe.PathString.string(srcInfo.path)}.{srcInfo.name} -> '
f'{ufe.PathString.string(dstInfo.path)}.{dstInfo.name}')
# Connect using `ufe.Attribute` objects.
item1Attributes = ufe.Attributes.attributes(items[1])
item1Out = item1Attributes.attribute('outputs:out')
item2Attributes = ufe.Attributes.attributes(items[2])
item2In = item2Attributes.attribute('inputs:in1')
connectionHandler.connect(item1Out, item2In)
print('Created connection: '
f'{ufe.PathString.string(item1Out.sceneItem().path())}.{item1Out.name} -> '
f'{ufe.PathString.string(item2In.sceneItem().path())}.{item2In.name}')
# Create a compound and a child node to demonstrate connections between parent and child nodes.
compound = lx.createCompound(shadingContainer)
ufe.Attributes.attributes(compound).addAttribute("inputs:foo", "ColorFloat3")
ufe.Attributes.attributes(compound).addAttribute("outputs:bar", "ColorFloat3")
child = ufe.NodeDef.definition(runTimeId, 'ND_add_color3').createNode(compound, ufe.PathComponent('child'))
# Create connections between parent and child. Note the `input -> input` and `output -> output`
# connections, as mentioned above.
connectionHandler.connect(ufe.AttributeInfo(compound.path(), 'inputs:foo'), ufe.AttributeInfo(child.path(), 'inputs:in1'))
connectionHandler.connect(ufe.AttributeInfo(child.path(), 'outputs:out'), ufe.AttributeInfo(compound.path(), 'outputs:bar'))
# The connection handler can also be used to view existing upstream connections of an item.
# Downstream connections are not accessible.
childConnectionsInterface = connectionHandler.sourceConnections(child)
print(f'Item "{ufe.PathString.string(child.path())}" has the following upstream connections:')
for connection in childConnectionsInterface.allConnections():
print('- '
f'{ufe.PathString.string(connection.src.path)}.{connection.src.name} -> '
f'{ufe.PathString.string(connection.dst.path)}.{connection.dst.name}')
# It can also be used to delete connections in the same two ways as they are created. Either using
# `ufe.AttributeInfo` or `ufe.Attribute` objects.
connectionHandler.disconnect(srcInfo, dstInfo)
print('Deleted connection: '
f'{ufe.PathString.string(srcInfo.path)}.{srcInfo.name} -> '
f'{ufe.PathString.string(dstInfo.path)}.{dstInfo.name}')