You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

75 lines
3.0 KiB

namespace UnityEngine.Rendering
{
// Q: What is this?
// A: A utility class for storing a reference to a ProbeVolumeBakingSet, without forcing the object to be loaded in-memory.
// Q: Why do we need this?
// A: APV uses a lot of global state, and we aren't always good with cleaning it up. Unity's serialization layer will automatically
// load referenced assets into memory, recursively. Some of the assets referenced by ProbeVolumeBakingSet can get very large, on
// the order of several gigabytes. A lingering global reference to a ProbeVolumeBakingSet can keep these assets in memory indefinitely,
// preventing them from being garbage collected. By using a weak reference, we prevent this - ProbeVolumeBakingSet can be freely
// garbage collected. Whenever we actually need to access it, we load it on-demand, if it isn't already in memory.
internal class ProbeVolumeBakingSetWeakReference
{
public int m_InstanceID;
public ProbeVolumeBakingSetWeakReference(ProbeVolumeBakingSet bakingSet)
{
Set(bakingSet);
}
public ProbeVolumeBakingSetWeakReference()
{
m_InstanceID = 0;
}
// Change which baking set the references points to.
public void Set(ProbeVolumeBakingSet bakingSet)
{
if (bakingSet == null)
m_InstanceID = 0;
else
m_InstanceID = bakingSet.GetInstanceID();
}
// Get the referenced baking set, loading it into memory if necessary.
public ProbeVolumeBakingSet Get()
{
return Resources.EntityIdToObject(m_InstanceID) as ProbeVolumeBakingSet;
}
// Is the referenced baking set in memory?
public bool IsLoaded()
{
return Resources.EntityIdIsValid(m_InstanceID);
}
// Force the referenced baking set to be unloaded from memory.
// Calling Get() after Unload() will re-load the baking set into memory.
public void Unload()
{
if (!IsLoaded())
return;
var bakingSet = Get();
// These assets would get garbage collected, but we clean them up immediately to free memory earlier.
// Only do this in editor, where the assets are never needed, so we don't unload assets that may still be in use.
#if UNITY_EDITOR
Resources.UnloadAsset(bakingSet.cellBricksDataAsset?.asset);
Resources.UnloadAsset(bakingSet.cellSharedDataAsset?.asset);
Resources.UnloadAsset(bakingSet.cellSupportDataAsset?.asset);
foreach (var scenario in bakingSet.scenarios)
{
Resources.UnloadAsset(scenario.Value.cellDataAsset?.asset);
Resources.UnloadAsset(scenario.Value.cellOptionalDataAsset?.asset);
Resources.UnloadAsset(scenario.Value.cellProbeOcclusionDataAsset?.asset);
}
#endif
// Unload the baking set itself.
Resources.UnloadAsset(bakingSet);
}
}
}