Translating Between the OpenUSD C++ and Python APIs

The USD APIs for C++ are well-defined at Pixar’s API Documentation . However, for Python there are some differences overall between C++ and Python which leads to confusion when you’re trying to call a function you know exists based on the documentation.

C++ vs Python

In the C++ USD API, classes are named using a pattern that always includes their high-level USD prefix. For example, UsdPrim or UsdGeomImageable both include Usd in the name (there are other high-level prefixes such as Sdf and Tf). However in Python classes are grouped into a hierarchy that is not always based on a common prefix, so extra attention is required to correlate C++ and Python classes.

For example, there is a Usd module inside the root pxr module (all of the USD API exists in the pxr module), but you won’t find C++’s UsdGeomImageable under Usd, or GeomImageable , instead UsdGeomImageable is found under UsdGeom.Imageable.

However C++’s ‘ UsdPrim class does exist under Usd , simply as Usd.Prim.

So when you read the API Documentation for UsdPrim or some other C++ class and you want to apply that information to Python, you need to drop some part of the class name from the beginning and turn it into the module. For example:

# analog to the UsdPrim() constructor in C++
from pxr import Usd

prim = Usd.Prim()

And to create a UsdGeomSphere it would be:

# analog to the UsdGeomSphere() constructor in C++
from pxr import Usd, UsdGeom

invalid_prim = Usd.Prim()
sphere = UsdGeom.Sphere(invalid_prim)

USD Python Module Names

Below is a list of Python Modules that are declared in the pxr module. These will help you find the translation between C++ and Python from the API Documentation. To find the equivalent class (for example UsdGeomSphere ), first find the longest prefix that appears in the list below (so UsdGeom), remove the prefix and refer to the class as the resulting string inside that module (so UsdGeom.Sphere).

Module Name

  • Ar

  • CameraUti

  • Garch

  • Gf

  • Glf

  • Kind

  • Ndr

  • Pcp

  • Plug

  • Sdf

  • Sdr

  • Tf

  • Trace

  • Usd (this contains important subclasses like UsdPrim )

  • UsdGeom

  • UsdHydra

  • UsdImagiGL

  • UsdLux

  • UsdRi

  • UsdSchemaExamples

  • UsdShade

  • UsdShaders

  • UsdSkel

  • UsdUI

  • UsdUtil

  • UsdVol

  • Vt

  • Work

If you’re wondering how to put this advice into practice, let’s try to find out how to refer to C++’s UsdLuxDistantLight’s Python API, specifically the UsdLuxDistantLight.GetAngleAttr() function:

  1. Look at the table above, and try to find the longest module name that exists in the name of UsdLuxDistantLight. You will see that it is UsdLux-DistantLight.

  2. Now, you can import that module and look inside to make sure that DistantLight is defined:

from pxr import UsdLux

# if you are in the Python REPL you can just write dir(UsdLux)
print(dir(UsdLux))

# Output is: ['BlackbodyTemperatureAsRgb', 'CylinderLight', 'DiskLight', 'DistantLight', 'DomeLight', 'GeometryLight', 'Light', 'LightFilter', 'LightPortal', 'ListAPI', 'RectLight', 'ShadowAPI', 'ShapingAPI', 'SphereLight', 'Tokens', '__MFB_FULL_PACKAGE_NAME', '__builtins__', '__cached__', '__doc__', '__file__', '__loader__', '__name__', '__package__', '__path__', '__spec__', '_usdLux']
  1. We can see that DistantLight is exposed as an object, and if we want to be sure we’re in the right spot we can repeat the above to see what is available within DistantLight:

from pxr import UsdLux

# if you are in the Python REPL you can just write dir(UsdLux.DistantLight)

print(dir(UsdLux.DistantLight))

# Output is: ['AddOrientOp', 'AddRotateXOp', 'AddRotateXYZOp', 'AddRotateXZYOp', 'AddRotateYOp', 'AddRotateYXZOp', 'AddRotateYZXOp', 'AddRotateZOp', 'AddRotateZXYOp', 'AddRotateZYXOp', 'AddScaleOp', ... snipped]
  1. Now you may be wondering why are there so many more exposed objects above versus the “Public Member Functions” on UsdLuxDistantLight’s API page, and that’s because UsdLuxDistantLight inherits from a few other classes (notably UsdLuxLight and UsdGeomXformable ), so we’re seeing the full object namespace. It is extremely useful to open the Inheritance Diagram in the C++ class’ API documentation that you’re inspecting, things become clear there.