using System; using XCEngine; using XCEngine.Rendering; namespace XCEngine.Rendering.Universal { public abstract class RendererBackedRenderPipelineAsset : ScriptableRenderPipelineAsset { public ScriptableRendererData[] rendererDataList = Array.Empty(); public int defaultRendererIndex = 0; protected RendererBackedRenderPipelineAsset() { } protected override ScriptableRenderPipeline CreatePipeline() { return CreateRendererBackedPipeline(); } protected override void ConfigureCameraRenderRequest( CameraRenderRequestContext context) { ConfigureRendererCameraRequest( new RendererCameraRequestContext(context)); ScriptableRendererData resolvedRendererData = GetDefaultRendererData(); if (resolvedRendererData != null) { resolvedRendererData .ConfigureCameraRenderRequestInstance( context); } } protected override void ConfigureCameraFramePlan( ScriptableRenderPipelinePlanningContext context) { ScriptableRendererData resolvedRendererData = GetDefaultRendererData(); if (resolvedRendererData != null) { resolvedRendererData .ConfigureCameraFramePlanInstance( context); } } protected override string GetPipelineRendererAssetKey() { ScriptableRendererData resolvedRendererData = GetDefaultRendererData(); return resolvedRendererData != null ? resolvedRendererData .GetPipelineRendererAssetKeyInstance() : string.Empty; } protected override void ReleaseRuntimeResources() { ReleaseRendererDataRuntimeResources(); } protected virtual ScriptableRenderPipeline CreateRendererBackedPipeline() { return new RendererBackedRenderPipeline(this); } protected virtual void ConfigureRendererCameraRequest( RendererCameraRequestContext context) { } protected virtual ScriptableRendererData CreateDefaultRendererData() { return null; } internal ScriptableRendererData GetDefaultRendererData() { return GetRendererData(defaultRendererIndex); } internal ScriptableRenderer GetDefaultRenderer() { return GetRenderer(defaultRendererIndex); } internal ScriptableRendererData GetRendererData( int rendererIndex) { EnsureRendererDataList(); if (rendererDataList.Length == 0) { return null; } int resolvedRendererIndex = ResolveRendererIndex(rendererIndex); if (resolvedRendererIndex < 0) { return null; } if (rendererDataList[resolvedRendererIndex] == null) { rendererDataList[resolvedRendererIndex] = CreateDefaultRendererData(); } return rendererDataList[resolvedRendererIndex]; } internal ScriptableRenderer GetRenderer( int rendererIndex) { ScriptableRendererData rendererData = GetRendererData(rendererIndex); return rendererData != null ? rendererData.GetRendererInstance() : null; } protected internal void ReleaseRendererDataRuntimeResources() { EnsureRendererDataList(); for (int i = 0; i < rendererDataList.Length; ++i) { ScriptableRendererData rendererData = rendererDataList[i]; if (rendererData == null || WasRendererDataReleasedEarlier(i)) { continue; } rendererData.ReleaseRuntimeResourcesInstance(); } } private void EnsureRendererDataList() { if (rendererDataList != null && rendererDataList.Length > 0) { return; } ScriptableRendererData defaultRendererData = CreateDefaultRendererData(); rendererDataList = defaultRendererData != null ? new ScriptableRendererData[] { defaultRendererData } : Array.Empty(); defaultRendererIndex = 0; } private bool WasRendererDataReleasedEarlier( int rendererDataIndex) { ScriptableRendererData rendererData = rendererDataList[rendererDataIndex]; for (int i = 0; i < rendererDataIndex; ++i) { if (object.ReferenceEquals( rendererDataList[i], rendererData)) { return true; } } return false; } private int ResolveRendererIndex( int rendererIndex) { EnsureRendererDataList(); if (rendererDataList.Length == 0) { return -1; } if (rendererIndex < 0 || rendererIndex >= rendererDataList.Length) { return ResolveDefaultRendererIndex(); } return rendererIndex; } private int ResolveDefaultRendererIndex() { EnsureRendererDataList(); if (rendererDataList.Length == 0) { return -1; } if (defaultRendererIndex < 0 || defaultRendererIndex >= rendererDataList.Length) { defaultRendererIndex = 0; } return defaultRendererIndex; } } }