Hey USD people!
A bit of a long one, so TLDR: we would like to propose encode a “dot” node in a NodeGraph; below are some options and reasonings.
We’ve been looking into the UsdShade space of USD and noticed that although there is a backdrop prim type, there is no “Dot” node prim, and no way to encode such a Prim in the node graph. These node types are common across multiple DCC’s in respect to building NodeGraphs (for shading or otherwise), and we’d like to get insight into some possible options we’re considering.
We have thought of three core approaches in mind for implementing Dot nodes with USD:
- A
nodeShapeUI Hint Metadata forNodeGraphprim which can accept dot as a valid value. - A new APISchema
NodeGraphDotNodeAPIwhich inherits fromNodeGraphNodeAPI- this allows for high level schema-based filtering and further visual or behavioural customization the API, such as changing the fallback of theexpansionStatetoclosed. DotNodeconcrete typed schema.
By utilising the existing UIHints metadata, it would be the smallest of changes. However, “nodeShape” does not necessarily fit with all prims which want to use the UIHints schemas as they are. It could also be custom metadata; in which case it does not need to be part of the UIHints schemas, but looses some of its impact as a standard metadata between DCC’s. Also since this would be set on the NodeGraph prim, we would inherit its connection behaviour and encapsulation rules. Also with a nodeShape hint, there is further scope for allowing other shapes for a prim representation.
As always these have different advantages and disadvantages.
-
Would be the most backwards compatible, and easy to retrofit support for, since its just another piece of metadata to read. However, it is limited in scope, and feels naïve . It also doesn’t necessarily make sense with the rest of the UIHints, since its likely only suited to NodeGraph prims, whereas the other UIHints are more globally useful.
-
Whether its an extension of
UsdUINodeGraphNodeAPIor a new API schema with inheritance, it similarly trivial to support, and even easier to add (especially if its a schema with inheritance) to existing scenes/USD builds via registration. Given it would only be applied to aNodeGraphprim, it would also function in other versions of USD, or builds without the schema, as aNodeGraphprim with its output connected to its own input; as a passthrough. We would also make use of expansion state to toggle between different view modes for the dot (either the traditional dot, or an expanded version which would look more like a “normal” node). As a new API schema it also allows for easier hiding in TreeViews, via aHasAPIquery, where seeing “dot” prims is superficial. We may also extend with custom methods on the API schema to handle automatically when an attribute is connected as an input to create the matching output and connect it automatically, and vice versa. -
Would put the Dot node in the same space as the
BackDropand allow for more fully fledged customisable behaviour. However, I feel this is the hardest to add support for in applications prior to any official inclusion.
Personally I prefer 2, however, we are interested in the wider USD communities feedback on this one before we make an official proposal or MR. I have attached a small example material which utilises option 2.
#usda 1.0
(
defaultPrim = "ups_textured"
)
def Material "ups_textured" (
kind = "group"
)
{
asset inputs:file = @C:/Users/JamesPedlingham/Pictures/UV_Checker.jpg@
string inputs:varname = "st"
token outputs:surface.connect = </ups_textured/UsdPreviewSurface5.outputs:surface>
def Shader "UsdPreviewSurface5" (
prepend apiSchemas = ["NodeGraphNodeAPI"]
)
{
token info:id = "UsdPreviewSurface"
color3f inputs:diffuseColor = (0.36605546, 0.6923519, 0.0010682017)
color3f inputs:diffuseColor.connect = </ups_textured/dot1.outputs:o1>
color3f inputs:emissiveColor.connect = </ups_textured/dot8.outputs:o1>
token outputs:surface
uniform token ui:nodegraph:node:expansionState = "open"
uniform float2 ui:nodegraph:node:pos = (-397, 626)
}
def NodeGraph "dot1"(
prepend apiSchemas = ["NodeGraphDotNodeAPI"]
)
{
color3f outputs:o1.connect = </ups_textured/dot1.inputs:i0>
color3f inputs:i1.connect = </ups_textured/UsdUVTexture2.outputs:rgb>
uniform float2 ui:nodegraph:node:pos = (-578, 649)
}
def NodeGraph "dot8"(
prepend apiSchemas = ["NodeGraphDotNodeAPI"]
)
{
color3f outputs:o1.connect = </ups_textured/dot8.inputs:i0>
color3f inputs:i1.connect = </ups_textured/UsdUVTexture2.outputs:rgb>
uniform token ui:nodegraph:node:expansionState = "open"
uniform float2 ui:nodegraph:node:pos = (-578, 649)
}
def Shader "UsdUVTexture2"(
prepend apiSchemas = ["NodeGraphNodeAPI"]
)
{
token info:id = "UsdUVTexture"
asset inputs:file = @C:/Users/JamesPedlingham/Pictures/UV_Checker.jpg@
asset inputs:file.connect = </ups_textured.inputs:file>
float2 inputs:st.connect = </ups_textured/UsdPrimvarReader_float4.outputs:result>
float3 outputs:rgb
uniform token ui:nodegraph:node:expansionState = "open"
uniform float2 ui:nodegraph:node:pos = (-678, 649)
}
def Shader "UsdPrimvarReader_float4"(
prepend apiSchemas = ["NodeGraphNodeAPI"]
)
{
token info:id = "UsdPrimvarReader_float2"
string inputs:varname = "st"
string inputs:varname.connect = </ups_textured.inputs:varname>
float2 outputs:result
uniform token ui:nodegraph:node:expansionState = "open"
uniform float2 ui:nodegraph:node:pos = (-988, 593)
}
}
As well as a small image of what that may look like with “open” and “closed” states of the dot node (mock designs, example based from Katana’s existing node graph with a few manual tweaks).
Interested to hear your thoughts!
James

