Is C++ API documentation for KIT APIs, Connector API and Nucleus API available?

Hi,

I couldn’t find C++ API documentation for the any of the Omniverse APIs.
There is some for the Python API of Omni Client, but nothing more.
Can you please add that documentation so that we can start testing if integrating Omniverse in our ecosystem would work?
Can you please also add licensing information for all the APIs and Frameworks you are providing as part of Omniverse(for personal as well as commercial use)?

Thanks,
Pratik

Hello pratikmankawde,
Thank you for the post, I have sent your request to the proper channels for review.
Thank you for your patience.

Thanks!

Hi Pratik,

There is a C++ Sample SDK for the Connector API. It is called the CONNECT SAMPLE in the Exchange under Connectors.

This should get you started connecting to Omniverse and provide a simple example of storing data in USD.

Brian

I wanted to provide some additional information to @bharrison excellent answer. The Omni Client API is the Nucleus API we expose for clients. It does currently not have separate HTML-based documentation for C++ (like we do for Python). Instead there is extensive header-based documentation which you will find in the different include files, for example here: connectsample-100.1.9_build\target-deps\omni_client_library\include\OmniClient.h. These files also include the license at the top and the combined list of licenses for the SDK can be found here: connectsample-100.1.9_build\target-deps\omni_client_library\PACKAGE-LICENSES.

Finally, we have a plan to publish and document a C++ API for Kit SDK as well but this is still work in progress and we cannot communicate a timeline for this work at this moment.

Hi @halldor, @bharrison
Thanks for the response.

I already checked the Connect Sample. Based on it, I actually wrote a connector prototype which connects our ecosystem with Omniverse. It works for some parts but crashes sometimes. Possible reason could be incorrect adaptation of Omniverse workflow. Like file locking, subscribing to event, when to and when not to call omniUsdLiveProcess() etc.
I have checked the OmniClient.h file for comments based docs but it doesn’t look complete. Like function parameters of omniClientListSubscribe. What are the possible correct values of url? What should be passed in as userData? What does OmniClientListSubscribeCallback carry in its userData field? Does OmniClientListSubscribeCallback needs to be defined as static function only? How can I subscribe to an event for a single file?

Until we get the C++ API framework docs, we cannot test the integration for Omniverse properly, hence can’t make the decision if we want to wait for its release or move on with some other framework. I hope you understand.

Hi Pratik,

Wow, glad you started using the Connect Sample. But bummer you are having crashes. Without seeing the whole code structure, here is something that could cause crashes:

Pathing names in USD have illegal characters in them … generally, you can have [a-z, A-Z, 0-9, _, ., /] and if you have anything else, you may get a crash or a hang during save. At least, that has been my experience when writing Connectors.

Let’s see if @bharris_nvidia can help answer the question about the callback (static, format of the user data).

And unfortunately, we don’t have a public timeline for the C++ API docs as @Halldor mentioned above.

I think if we can get your data into Omniverse as a test, then we can go from there on other needs.

Brian

I am just creating a cube mesh in USD, nothing fancy. The apps crash when I change transform of the cube on one end(my app) and then try to change it again on another app(Create, or vise-versa), not all the time but often. Maya doesn’t receive the changes at all from my app or even Create app. Any changes made in Maya does reflect in (only)Create though.
I made sure so special characters are in use in any of the names or paths in USD.

One thing that could cause you problems in your app with USD is if a transform exists and you try to define it again, that can fail. You would need to check to see if the transform exists and then modify it in that case.

@LouRohan Do you have other ideas here?

Th live workflow or the transform code in your app could be the culprit here (as indicated). I suppose you scoured the helloWorld.cpp liveEdit(...) function. This deals with both live updates in a very simple blocking loop and transform code, notably:

Live;

  • start: block for keyboard input
  • omniUsdLiveWaitForPendingUpdates()
  • read and set the prim’s xform
  • commit the change to USD with a stage Save() call
  • go to start

Transforms:
The USD transform options often lead to some gnarly utility functions because they are so flexible. I would make sure that your app examines the xform ops stack and processes transform changes accordingly. For example, look at what op stack Create gives the mesh and ensure that your app can observe it change (before trying to set anything). Create and Maya should use the same xform ops stacks, but it’s possible they don’t, so also look at that and see if you can first receive changes.

After going through this description for you I wonder if we shouldn’t add an example of how to listen for stage updates, rather than using a simple polling mechanism like the sample does currently. I’ll look into adding something like this and it would probably be beneficial for what your app is trying to do.

Hi @LouRohan / Team OV, I was wondering if anyone might have a bit of example code handy showing how to subscribe to stage update events as I’m struggling to figure out the correct functions to call also (and in which order).

Which subscription function(s) should I be using if I just wanted to get live scene graph transform updates for a specific USD scene on my server? And do I subscribe to the events and then enter a busy loop or… perhaps call a function in the busy loop to pass control back to the client API each time around (with some kind of throttling…?)

Thanks,

Sam

I may have figured it out actually. Does this look like the correct pattern for subscribing to remote updates on a usd? Or are there different recommendations?

static UsdStageRefPtr gStage;

static void sync() noexcept
{
    auto range = gStage->Traverse();
    for (const auto& node : range)
    {
        {
            std::unique_lock<std::mutex> lk(gLogMutex);
            std::cout << "NODE: " << node.GetName() << std::endl;
            // >>> Sync node to my internal scene representation here (if different)
        }
    }
}

static void OmniClientStatCallbackImpl(void* userData, OmniClientResult result, struct OmniClientListEntry const* entry) noexcept
{
    // Initial full sync
    sync();
}

static void OmniClientStatSubscribeCallbackImpl(void* userData, OmniClientResult result, OmniClientListEvent listEvent, struct OmniClientListEntry const* entry) noexcept
{
    // Incremental sync
    sync();
}

std::string stagePath = "omniverse://MY_NUCLEUS_IP/SOME_PATH/Test.usd";
gStage = UsdStage::Open(stagePath);
if (!gStage)
{
    failNotify("Failed to open Omiverse stage:", stagePath.c_str());
    return 1;
}

omniClientStatSubscribe(stagePath.c_str(), CUSTOM_DATA_IF_I_WANT, OmniClientStatCallbackImpl, OmniClientStatSubscribeCallbackImpl);

while (true)
{
    std::this_thread::sleep_for (std::chrono::milliseconds(10));
    // Do other appy stuff here instead of sleeping..
}

Thanks,

Sam