検索 - User list
Full Version: SOP->LOP Material Workflow
Root » Solaris and Karma » SOP->LOP Material Workflow
SpeedOfLight
Hey all,

Is there a recommended SOP->LOP workflow with materials? We'd like to assign materials in SOPs and have them carry over to UsdShade in LOPS.

VOP Materials assigned in LOPs create UsdShade references *and* translated USD preview shaders. However, materials assigned in SOP and imported into LOPs with default settings preserve the shop_materialpathproperty as primvars::shop_materialpathbut no UsdShade material slots or bindings are created in the output LOP stage.

Is there a node that performs this linking automagically?

Otherwise, is there a conceptual difference preventing a node like this from being published?

Thanks!
jsmack
SOP Create imports materials and performs assignments to geometry subsets based on shop_materialpath values. The primvars:shop_materialpath is superfluous, and can be filtered using the sop import attribute settings.

I'm not sure if there is another node that translates materials and assignments the way sop create does. Scene import will import geometry and materials, but I don't know how it handles materials assigned at geometry level.
SpeedOfLight
@jsmack, this isn't the behavior I'm experiencing. I get a USD output without a binding, just a shop_materialpath primvar in partitions.

Attached below is the repro.

Houdini Core Version 18.0.287

Repro steps:

1. in /stage, create a “Sop Create” node
2. in /mat, create a principled shader, select teal as an emissive color.
3. in /stage/sopcreate1, create a “box” and assign it the material via “material” node.
4. material will appear teal inside /stage/sopcreate1/sopnet/create.
5. in /stage, right-click sopnet1 -> LOP Options -> Inspect Flattened Stage.


Output USD:
#usda 1.0
(
defaultPrim = "sopcreate1"
doc = """Generated from Composed Stage of root layer
"""
)

def Xform "sopcreate1" (
kind = "component"
)
{
matrix4d xformOp:transform:xform = ( (1, 0, 0, 0), (0, 1, 0, 0), (0, 0, 1, 0), (0, 0, 0, 1) )
uniform token[] xformOpOrder = ["xformOp:transform:xform"]

def Mesh "mesh_0"
{
float3[] extent = [(-0.5, -0.5, -0.5), (0.5, 0.5, 0.5)]
int[] faceVertexCounts = [4, 4, 4, 4, 4, 4] (
customData = {
int64 HoudiniDataId = 2654593799
}
)
int[] faceVertexIndices = [1, 5, 4, 0, 2, 6, 5, 1, 3, 7, 6, 2, 0, 4, 7, 3, 2, 1, 0, 3, 5, 6, 7, 4] (
customData = {
int64 HoudiniDataId = 2654593799
}
)
uniform token orientation = "leftHanded"
point3f[] points = [(-0.5, -0.5, -0.5), (0.5, -0.5, -0.5), (0.5, -0.5, 0.5), (-0.5, -0.5, 0.5), (-0.5, 0.5, -0.5), (0.5, 0.5, -0.5), (0.5, 0.5, 0.5), (-0.5, 0.5, 0.5)] (
customData = {
int64 HoudiniDataId = 158027
}
interpolation = "vertex"
)
uniform token subdivisionScheme = "none"
uniform token subsetFamily:shop_materialpath:familyType = "partition"

def GeomSubset "shop_materialpath__mat_principledshader1" (
customData = {
string partitionValue = "/mat/principledshader1"
}
)
{
uniform token familyName = "shop_materialpath"
int[] indices = [0, 1, 2, 3, 4, 5]
}
}
}

def HoudiniLayerInfo "HoudiniLayerInfo" (
customData = {
string HoudiniCreatorNode = "/stage/sopcreate1/sopimport"
string[] HoudiniEditorNodes = ["/stage/sopcreate1/sopnet/OUT", "/stage/sopcreate1/sopimport", "/stage/sopcreate1/merge1", "/stage/sopcreate1/xform"]
string HoudiniSaveControl = "Placeholder"
}
)
{
}
jsmack
The materials aren't dynamic. Click the auto-fill button on the material tab to create material prims corresponding to the shop_materialpath values.

#usda 1.0
(
    defaultPrim = "tetrahedron"
    doc = """Generated from Composed Stage of root layer 
"""
)

def Xform "tetrahedron" (
    kind = "component"
)
{
    matrix4d xformOp:transform:xform = ( (1, 0, 0, 0), (0, 1, 0, 0), (0, 0, 1, 0), (0, 0, 0, 1) )
    uniform token[] xformOpOrder = ["xformOp:transform:xform"]

    def Mesh "mesh_0"
    {
        float3[] extent = [(-0.9428103, -0.3333297, -0.8164976), (0.47140515, 1, 0.8164976)]
        int[] faceVertexCounts = [3, 3, 3, 3] (
            customData = {
                int64 HoudiniDataId = 2654461245
            }
        )
        int[] faceVertexIndices = [0, 3, 2, 0, 1, 3, 0, 2, 1, 1, 2, 3] (
            customData = {
                int64 HoudiniDataId = 2654461245
            }
        )
        normal3f[] normals = [(0.9428086, 0.33333457, -0), (-0.47140425, 0.33333454, -0.81649625), (-0.47140425, 0.33333454, 0.81649625), (0, -1, 0)] (
            customData = {
                int64 HoudiniDataId = 29748
            }
            interpolation = "uniform"
        )
        uniform token orientation = "leftHanded"
        point3f[] points = [(0, 1, 0), (-0.9428103, -0.3333297, 0), (0.47140515, -0.3333297, 0.8164976), (0.47140515, -0.3333297, -0.8164976)] (
            customData = {
                int64 HoudiniDataId = 25469
            }
            interpolation = "vertex"
        )
        uniform token subdivisionScheme = "none"
        uniform token subsetFamily:shop_materialpath:familyType = "partition"

        def GeomSubset "shop_materialpath__mat_teal" (
            customData = {
                string partitionValue = "/mat/teal"
            }
        )
        {
            uniform token familyName = "shop_materialpath"
            int[] indices = [0, 1, 2, 3]
        }
    }

    def Xform "materials"
    {
        def Material "teal" (
            customData = {
                int64 HoudiniMaterialId = 2
                int HoudiniPrimEditorNodeId = 26
            }
        )
        {
            token outputs:karma:displacement.connect = </tetrahedron/materials/teal/teal_displace.outputs:displacement>
            token outputs:karma:surface.connect = </tetrahedron/materials/teal/teal_surface.outputs:surface>
            token outputs:surface.connect = </tetrahedron/materials/teal/teal_preview.outputs:surface>

            def Shader "teal_surface"
            {
                uniform token info:implementationSource = "sourceAsset"
                uniform asset info:sourceAsset = @opdef:/Vop/principledshader::2.0?SurfaceVexCode@
                vector3f inputs:basecolor = (0.075, 0.3, 0.1875)
                float inputs:ior = 1.447
                float inputs:rough = 0.19
                token outputs:surface
            }

            def Shader "teal_displace"
            {
                uniform token info:implementationSource = "sourceAsset"
                uniform asset info:sourceAsset = @opdef:/Vop/principledshader::2.0?DisplacementVexCode@
                token outputs:displacement
            }

            def Shader "teal_preview"
            {
                uniform token info:id = "UsdPreviewSurface"
                float inputs:clearcoatRoughness = 0
                color3f inputs:diffuseColor = (0.075, 0.3, 0.1875)
                float inputs:ior = 1.447
                float inputs:roughness = 0.19
                color3f inputs:specularColor = (0.075, 0.3, 0.1875)
                token outputs:surface
            }
        }
    }
}

def HoudiniLayerInfo "HoudiniLayerInfo" (
    customData = {
        string HoudiniCreatorNode = "/stage/tetrahedron/materiallibrary"
        string[] HoudiniEditorNodes = ["/stage/tetrahedron/materiallibrary", "/stage/tetrahedron/merge1", "/stage/tetrahedron/assignmaterial", "/stage/tetrahedron/xform"]
        string HoudiniSaveControl = "Placeholder"
    }
)
{
}
SpeedOfLight
Thanks so much @jsmack!

I noticed this feature only exists in “SOP Create”, not in “SOP Import”. Is there a reason / are there plans to add support for material imports with “SOP Import”?

Additionally, I see “Scene Import (All)” will import materials as “SOP Create” does, the primitives retain the primvars::shop_materialpathattributes but they don't get linked to the imported materials via UsdShade.

Is there a different intended workflow for this design?

Thanks!
jsmack
SpeedOfLight
Thanks so much @jsmack!

I noticed this feature only exists in “SOP Create”, not in “SOP Import”. Is there a reason / are there plans to add support for material imports with “SOP Import”?

Sop Create is an HDA (Digital Asset) which combines the material library with a sop import. I would guess that no, it won't be coming to sop import unless they change the scope of it's functionality.

SpeedOfLight
Additionally, I see “Scene Import (All)” will import materials as “SOP Create” does, the primitives retain the primvars::shop_materialpathattributes but they don't get linked to the imported materials via UsdShade.

Is there a different intended workflow for this design?

Thanks!

The primvar is a red herring. All attributes are translated to usd primvars by default. It's simply a naive copy, and has nothing to do with the material bindings. I believe the Scene Import tool will preserve object level material bindings, but not SOP ones. The material section of the scene import can configure the scope of materials to translate to prims.
9krausec
Good thread! Would anyone have any pointers in how to use a wrangle to partition all USD “Mesh” primitives into “GeomSubset” primitives under the mesh? Recreating the ‘partitionattribs’ functionality of the ‘SOP Import’ LOP, but across all mesh objects on stage.

Going over the vex functions for USD now, but haven't cracked it yet. Thanks.

EDIT: Think I may have figured this out. Will update with solution after I make a solid example.
rafal
9krausec
Would anyone have any pointers in how to use a wrangle to partition all USD “Mesh” primitives into “GeomSubset”
There is also a Geometry Subset VOP LOP, with mode parameter set to “partition” and vex source to “vexpression”.
9krausec
Rafal, using Geometry Subset VOP LOP as you recommended was far more straightforward (and probably more efficient) than writing it all out in VEX. Got it working. Thank you, thank you.

My setup below for folks looking for this in the future -

Attached parameters.
Vex expression below,
string shop_materialpath[] = usd_attrib(0, @primpath, 'primvars:shop_materialpath');
string path = shop_materialpath[@elemnum];
string dir, name;
splitpath(path, dir, name);
return name;
OmerShapira
I noticed that SOP Create doesn't support material overrides: They don't get carried over, nor is another material with overrides created in UsdShade.
Are there plans to add material override support?
mtucker
That is not currently in the plan, no.
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Powered by DjangoBB