AssetContainers vs. SetEnabled

What are the tradeoffs between using AssetContainers and Node.SetEnabled() to “add/remove” items from a scene?

Here is a simple PG showing the two options:

My understanding is that AssetContainer is an abstract scene itself, and so acts as a temporary holder of assets that are moved in to it. Putting an item in the container completely removes it from the current scene.

I haven’t yet researched exactly what setEnabled does, but I assume it removes the node from the rendering pipeline, even though it remains in the scene.

At first glance, AssetContainer might seem the more efficient when needing to move nodes in/out of scenes. It also supports items other than Nodes. However, for nodes specifically, could AssetContainer have been implemented with SetEnabled instead? What would be the tradeoffs?

I think my question is useful regardless of my motivation for asking it, but in case it matters…

The reason for asking is that I believe the currently recommended approach for switching between multiple “scenes” in WebXR is to use an AssetContainer for moving items in/out of the scene as needed. (The other option is to render multiple scenes in a single render loop, but I think that’s inefficient and might have other problems.)

However, I’m finding that having to manage assets using AssetContainers to be complex with WebXR. (Consider that once WebXR is initialized, we can’t simply use methods like moveAllFromScene. See this issue for details.)

Some of the complexities are evident in this previous thread by @MarkM. For example, I’m parenting GUI items to controllers that can come and go. i.e. If I switch “scene”, I also need to cleanup the GUI elements attached to the controllers, etc. This is all doable with AssetContainers …it just gets complex. So before I invest too much more in to this approach, I wanted to first make sure AssetContainers are still the best option. If I were to implement a more custom approach, setEnabled seems very relevant.

I am usually quite happy relying only on setEnabled :slight_smile: it is just sometimes harder if you go through your scene objects as you need to bypass any disabled nodes (or through their parents)

Efficiency wise, it might even perform better on small amount of “root nodes” at the expense of feeling “less clean”

1 Like

I think the AssetContainer approach is probably the right approach but it is a bit under-baked at present. Mainly because it keeps things clean and i suspect with lots of larger scenes it might be the go, and be more managable/maintainable.

The things I did to get it nicer for me was to lift some of the code from moveAllFromScene to create a syncFromScene that adds any items from the scene that are not already in the AssetContainer (ie dont just add blindly but check includes first) and NOT remove it from the scene. I also have callbacks in the base/boot scene that checks for new items and adds them to its keepAssets if needed, eg webxr things.

I also created event hooks for onBeforeLoad, onAfterLoad, onBeforeUnload and onAfterUnload where i could do specific setups for the scene, eg set gravity, scene.ambientColor etc.

All of this was done on a class that inherits from AssetContainer.

There might have been more and i will check when i have my computer on again. I have just been hammered by a massive storm and am in stages of mopping up and getting secure.

And i know i should do a pull request for this, i would like to. But i am working in JS and not TS yet and i have been pulled onto other pressing (non-BJS) projects. That being said, my work contract is about to end so i may have more free time very soon :slight_smile: