feat(srp): formalize renderer contracts and project feature bridge

This commit is contained in:
2026-04-20 15:03:45 +08:00
parent 10b092d467
commit a615f78e72
13 changed files with 1604 additions and 28 deletions

View File

@@ -23,6 +23,7 @@ namespace XCEngine.Rendering
internal int GetRuntimeResourceVersionInstance()
{
SynchronizeRuntimeResourceVersion();
return m_runtimeResourceVersion;
}
@@ -55,6 +56,10 @@ namespace XCEngine.Rendering
{
}
protected virtual void SynchronizeRuntimeResourceVersion()
{
}
protected void SetDirty()
{
ReleaseRuntimeResources();

View File

@@ -60,7 +60,7 @@ namespace XCEngine.Rendering.Universal
if (m_pass == null)
{
Create();
CreateInstance();
}
renderer.EnqueuePass(m_pass);

View File

@@ -17,7 +17,7 @@ namespace XCEngine.Rendering.Universal
RendererRecordingContext context)
{
return m_asset != null
? m_asset.GetDefaultRenderer()
? m_asset.ResolveSelectedRenderer()
: null;
}
}

View File

@@ -10,6 +10,8 @@ namespace XCEngine.Rendering.Universal
public ScriptableRendererData[] rendererDataList =
Array.Empty<ScriptableRendererData>();
public int defaultRendererIndex = 0;
private int m_rendererDataRuntimeStateHash;
private bool m_rendererDataRuntimeStateHashResolved;
protected RendererBackedRenderPipelineAsset()
{
@@ -27,7 +29,7 @@ namespace XCEngine.Rendering.Universal
new RendererCameraRequestContext(context));
ScriptableRendererData resolvedRendererData =
GetDefaultRendererData();
ResolveSelectedRendererData();
if (resolvedRendererData != null)
{
resolvedRendererData
@@ -40,7 +42,7 @@ namespace XCEngine.Rendering.Universal
ScriptableRenderPipelinePlanningContext context)
{
ScriptableRendererData resolvedRendererData =
GetDefaultRendererData();
ResolveSelectedRendererData();
if (resolvedRendererData != null)
{
resolvedRendererData
@@ -52,7 +54,7 @@ namespace XCEngine.Rendering.Universal
protected override string GetPipelineRendererAssetKey()
{
ScriptableRendererData resolvedRendererData =
GetDefaultRendererData();
ResolveSelectedRendererData();
return resolvedRendererData != null
? resolvedRendererData
.GetPipelineRendererAssetKeyInstance()
@@ -64,6 +66,29 @@ namespace XCEngine.Rendering.Universal
ReleaseRendererDataRuntimeResources();
}
protected override void SynchronizeRuntimeResourceVersion()
{
int runtimeStateHash =
ComputeRendererDataRuntimeStateHash();
if (!m_rendererDataRuntimeStateHashResolved)
{
m_rendererDataRuntimeStateHash =
runtimeStateHash;
m_rendererDataRuntimeStateHashResolved = true;
return;
}
if (runtimeStateHash ==
m_rendererDataRuntimeStateHash)
{
return;
}
m_rendererDataRuntimeStateHash =
runtimeStateHash;
SetDirty();
}
protected virtual ScriptableRenderPipeline
CreateRendererBackedPipeline()
{
@@ -83,37 +108,34 @@ namespace XCEngine.Rendering.Universal
internal ScriptableRendererData GetDefaultRendererData()
{
return GetRendererData(defaultRendererIndex);
return ResolveSelectedRendererData();
}
internal ScriptableRenderer GetDefaultRenderer()
{
return GetRenderer(defaultRendererIndex);
return ResolveSelectedRenderer();
}
internal ScriptableRendererData ResolveSelectedRendererData()
{
return ResolveRendererDataByResolvedIndex(
ResolveSelectedRendererIndex());
}
internal ScriptableRenderer ResolveSelectedRenderer()
{
ScriptableRendererData rendererData =
ResolveSelectedRendererData();
return rendererData != null
? rendererData.GetRendererInstance()
: null;
}
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];
return ResolveRendererDataByResolvedIndex(
ResolveRendererIndex(rendererIndex));
}
internal ScriptableRenderer GetRenderer(
@@ -182,6 +204,60 @@ namespace XCEngine.Rendering.Universal
return false;
}
private int ComputeRendererDataRuntimeStateHash()
{
unchecked
{
int hash = 17;
hash =
(hash * 31) +
ResolveSelectedRendererIndex();
if (rendererDataList == null)
{
return hash;
}
hash = (hash * 31) + rendererDataList.Length;
for (int i = 0; i < rendererDataList.Length; ++i)
{
ScriptableRendererData rendererData =
rendererDataList[i];
if (rendererData != null)
{
hash =
(hash * 31) +
rendererData
.GetRuntimeStateVersionInstance();
}
}
return hash;
}
}
private ScriptableRendererData ResolveRendererDataByResolvedIndex(
int resolvedRendererIndex)
{
EnsureRendererDataList();
if (resolvedRendererIndex < 0)
{
return null;
}
if (rendererDataList[resolvedRendererIndex] == null)
{
rendererDataList[resolvedRendererIndex] =
CreateDefaultRendererData();
}
return rendererDataList[resolvedRendererIndex];
}
private int ResolveSelectedRendererIndex()
{
return ResolveRendererIndex(defaultRendererIndex);
}
private int ResolveRendererIndex(
int rendererIndex)
{

View File

@@ -69,7 +69,7 @@ namespace XCEngine.Rendering.Universal
}
m_features.Add(feature);
feature.Create();
feature.CreateInstance();
}
protected virtual void AddRenderPasses(

View File

@@ -9,6 +9,7 @@ namespace XCEngine.Rendering.Universal
private ScriptableRendererFeature[] m_rendererFeatures;
private ScriptableRenderer m_rendererInstance;
private bool m_rendererInvalidated;
private int m_runtimeStateVersion = 1;
protected ScriptableRendererData()
{
@@ -60,6 +61,11 @@ namespace XCEngine.Rendering.Universal
return GetPipelineRendererAssetKey();
}
internal int GetRuntimeStateVersionInstance()
{
return m_runtimeStateVersion;
}
internal void ReleaseRuntimeResourcesInstance()
{
ReleaseRendererSetupCache();
@@ -182,6 +188,15 @@ namespace XCEngine.Rendering.Universal
{
ReleaseRendererSetupCache();
m_rendererInvalidated = true;
unchecked
{
++m_runtimeStateVersion;
}
if (m_runtimeStateVersion <= 0)
{
m_runtimeStateVersion = 1;
}
}
protected void AddRendererFeature(

View File

@@ -6,6 +6,7 @@ namespace XCEngine.Rendering.Universal
public abstract class ScriptableRendererFeature
{
private bool m_disposed;
private bool m_runtimeCreated;
protected ScriptableRendererFeature()
{
@@ -13,6 +14,18 @@ namespace XCEngine.Rendering.Universal
public bool isActive { get; set; } = true;
internal void CreateInstance()
{
if (m_runtimeCreated)
{
return;
}
m_disposed = false;
Create();
m_runtimeCreated = true;
}
internal void ReleaseRuntimeResourcesInstance()
{
if (m_disposed)
@@ -22,6 +35,7 @@ namespace XCEngine.Rendering.Universal
ReleaseRuntimeResources();
m_disposed = true;
m_runtimeCreated = false;
}
public virtual void Create()