NVIDIA Warp is a Python framework for writing high-performance simulation and graphics code in Omniverse. Warp provides an easy way for Python coders to write kernel-based programs, and benefit from GPU-acceleration in Omniverse and OmniGraph.
NVIDIA’s Omniverse developers are using Warp to help create new GPU-accelerated 3D simulation workflows and dynamic content today. Some of the key benefits include simulation performance on-par with native code, and improved developer productivity thanks to fast iteration times.
In Warp, kernels are defined in Python syntax and JIT compiled to C++/CUDA at runtime. Users can hot-reload kernels directly from within Python, and leverage rich high-level data structures and algorithms to to build real-time simulations.
To get started with Warp in Omniverse users should enable the bundled extension from the extension registry (note that version may differ):
This will install the Warp extension into the Omniverse Python environment and allow users to import the module in their scripts and nodes. For example, once installed, users should be able to open the Script Editor window and execute the following code successfully:
import warp print(warp.config.version)
Kernels in Warp are defined using a
@wp.kernel decorator around user Python functions. For example, a simple function to deform a mesh according to a sine-wave could be defined as follows:
@wp.kernel def deform(points_in: wp.array(dtype=wp.vec3), points_out: wp.array(dtype=wp.vec3), time: float): # get thread-id tid = wp.tid() # sine-wave deformer points_out[tid] = points_in[tid] + wp.vec3(0.0, wp.sin(time + points_in[tid])*10.0, 0.0)
One of the main uses for Warp is as a convenient and productive way to define GPU OmniGraph nodes from Python. Below, we show the source for a node that deforms a set of mesh points using the kernel above, and outputs the result. The node’s
compute() method is responsible for wrapping input data arrays in a
wp.array() which ensures data is uploaded to the GPU, then launches our kernel on the device:
class OgnDeform: @staticmethod def compute(db) -> bool: with wp.ScopedCudaGuard(): # convert node inputs to a GPU array points_in = wp.array(db.inputs.points, dtype=wp.vec3, device="cuda") points_out = wp.zeros_like(points_in) # launch deformation kernel wp.launch(kernel=deform, dim=len(points_in), inputs=[points_in, points_out, db.inputs.time], device="cuda") # write node outputs db.outputs.points = points_out.numpy() return True
On first launch the
deform function will be JIT compiled to a native CUDA kernel and executed on the GPU. After execution, the result can be converted back to numpy arrays using the
array.numpy() method and assigned to the node outputs.
If we wire a USD mesh primitive to our node, we have a simple deformer that generates the following result:
The source code and USD for this example scene can be found in the Warp extension directory: