using System; using System.Collections.Generic; using UnityEngine.Serialization; #if UNITY_EDITOR using UnityEditor; #endif namespace UnityEngine.Rendering { /// /// A component that stores baked probe volume state and data references. Normally hidden in the hierarchy. /// [ExecuteAlways] [AddComponentMenu("")] // Hide. public class ProbeVolumePerSceneData : MonoBehaviour { /// The baking set this scene is part of. public ProbeVolumeBakingSet bakingSet => serializedBakingSet; // Warning: this is the baking set this scene was part of during last bake // It shouldn't be used while baking as the scene may have been moved since then [SerializeField, FormerlySerializedAs("bakingSet")] internal ProbeVolumeBakingSet serializedBakingSet; [SerializeField] internal string sceneGUID = ""; // All code bellow is only kept in order to be able to cleanup obsolete data. [Serializable] internal struct ObsoletePerScenarioData { public int sceneHash; public TextAsset cellDataAsset; // Contains L0 L1 SH data public TextAsset cellOptionalDataAsset; // Contains L2 SH data } [Serializable] struct ObsoleteSerializablePerScenarioDataItem { #pragma warning disable 649 // is never assigned to, and will always have its default value public string scenario; public ObsoletePerScenarioData data; #pragma warning restore 649 } [FormerlySerializedAs("asset")] [SerializeField] internal ObsoleteProbeVolumeAsset obsoleteAsset; [FormerlySerializedAs("cellSharedDataAsset")] [SerializeField] internal TextAsset obsoleteCellSharedDataAsset; // Contains bricks and validity data [FormerlySerializedAs("cellSupportDataAsset")] [SerializeField] internal TextAsset obsoleteCellSupportDataAsset; // Contains debug data [FormerlySerializedAs("serializedScenarios")] [SerializeField] List obsoleteSerializedScenarios = new(); #if UNITY_EDITOR void DeleteAsset(Object asset) { if (asset != null && AssetDatabase.TryGetGUIDAndLocalFileIdentifier(asset, out string guid, out long instanceID)) { var assetPath = AssetDatabase.GUIDToAssetPath(guid); AssetDatabase.DeleteAsset(assetPath); } } #endif internal void Clear() { QueueSceneRemoval(); serializedBakingSet = null; #if UNITY_EDITOR EditorUtility.SetDirty(this); #endif } internal void QueueSceneLoading() { if (serializedBakingSet == null) return; #if UNITY_EDITOR // Check if we are trying to load APV data for a scene which has not enabled APV (or it was removed) var bakedData = serializedBakingSet.GetSceneBakeData(sceneGUID); if (bakedData != null && bakedData.hasProbeVolume == false) return; #endif var refVol = ProbeReferenceVolume.instance; refVol.AddPendingSceneLoading(sceneGUID, serializedBakingSet); } internal void QueueSceneRemoval() { if (serializedBakingSet != null) ProbeReferenceVolume.instance.AddPendingSceneRemoval(sceneGUID); } void OnEnable() { #if UNITY_EDITOR // In the editor, always refresh the GUID as it may become out of date is scene is duplicated or other weird things // This field is serialized, so it will be available in standalones, where it can't change anymore var newGUID = gameObject.scene.GetGUID(); if (newGUID != sceneGUID) { sceneGUID = newGUID; EditorUtility.SetDirty(this); } #endif ProbeReferenceVolume.instance.RegisterPerSceneData(this); } void OnDisable() { QueueSceneRemoval(); ProbeReferenceVolume.instance.UnregisterPerSceneData(this); } private void OnValidate() { #if UNITY_EDITOR // Cleanup old obsolete data. if (obsoleteAsset != null) { DeleteAsset(obsoleteAsset); DeleteAsset(obsoleteCellSharedDataAsset); DeleteAsset(obsoleteCellSupportDataAsset); foreach(var scenario in obsoleteSerializedScenarios) { DeleteAsset(scenario.data.cellDataAsset); DeleteAsset(scenario.data.cellOptionalDataAsset); } obsoleteAsset = null; obsoleteCellSharedDataAsset = null; obsoleteCellSupportDataAsset = null; obsoleteSerializedScenarios = null; EditorUtility.SetDirty(this); } #endif } internal void Initialize() { ProbeReferenceVolume.instance.RegisterBakingSet(this); QueueSceneRemoval(); QueueSceneLoading(); } internal bool ResolveCellData() { if (serializedBakingSet != null) return serializedBakingSet.ResolveCellData(serializedBakingSet.GetSceneCellIndexList(sceneGUID)); return false; } } }