2025-11-20 17:29:16 +08:00
|
|
|
|
using Convention.Collections;
|
|
|
|
|
|
using Convention.Collections.Generic;
|
2025-11-14 17:14:08 +08:00
|
|
|
|
using Convention.Experimental.PublicType;
|
2025-11-20 17:29:16 +08:00
|
|
|
|
using Convention.ReferenceManagement;
|
2025-11-13 16:39:25 +08:00
|
|
|
|
using System;
|
|
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
|
|
|
|
|
|
|
namespace Convention.Experimental
|
|
|
|
|
|
{
|
|
|
|
|
|
public static class Architecture
|
|
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
private static readonly LinkedCacheList<object> s_GameFrameworkModules = new();
|
2025-11-13 16:39:25 +08:00
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
2025-11-20 16:17:10 +08:00
|
|
|
|
/// <20><><EFBFBD><EFBFBD>ʵ<EFBFBD><CAB5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
2025-11-13 16:39:25 +08:00
|
|
|
|
/// </summary>
|
2025-11-20 16:17:10 +08:00
|
|
|
|
/// <param name="instanceType">Ҫ<><D2AA><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD></param>
|
|
|
|
|
|
/// <returns>Ŀ<><C4BF>ʵ<EFBFBD><CAB5></returns>
|
|
|
|
|
|
private static object Create(Type instanceType, int stackLayer = 0)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-14 17:14:08 +08:00
|
|
|
|
if (stackLayer >= 100)
|
|
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
throw new GameException($"Create instance '{instanceType.FullName}' failed, recursion too deep, there may be a circular dependency.");
|
2025-11-14 17:14:08 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2025-11-20 16:17:10 +08:00
|
|
|
|
object instance = Activator.CreateInstance(instanceType);
|
|
|
|
|
|
if (instance == null)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
throw new GameException($"Can not create instance '{instanceType.FullName}'");
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2025-11-20 16:17:10 +08:00
|
|
|
|
if (instance is GameModule module)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
// <20>ݹ鴴<DDB9><E9B4B4><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ģ<EFBFBD><C4A3>
|
|
|
|
|
|
foreach (var dependenceType in module.Dependences())
|
|
|
|
|
|
_ = Get(dependenceType, stackLayer + 1);
|
|
|
|
|
|
|
|
|
|
|
|
var current = s_GameFrameworkModules.First;
|
|
|
|
|
|
while (current != null)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
if (current.Value is GameModule nextModule && module.Priority > nextModule.Priority)
|
|
|
|
|
|
{
|
|
|
|
|
|
break;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
current = current.Next;
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2025-11-20 16:17:10 +08:00
|
|
|
|
if (current != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
s_GameFrameworkModules.AddBefore(current, module);
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
s_GameFrameworkModules.AddLast(module);
|
|
|
|
|
|
}
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2025-11-20 16:17:10 +08:00
|
|
|
|
return instance;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
|
/// <20><>ȡʵ<C8A1><CAB5>
|
|
|
|
|
|
/// </summary>
|
|
|
|
|
|
/// <param name="instanceType">Ҫ<><D2AA>ȡ<EFBFBD><C8A1>ʵ<EFBFBD><CAB5><EFBFBD><EFBFBD><EFBFBD><EFBFBD></param>
|
|
|
|
|
|
/// <returns>ʵ<><CAB5></returns>
|
|
|
|
|
|
/// <remarks><3E><><EFBFBD><EFBFBD>Ҫ<EFBFBD><D2AA>ȡ<EFBFBD><C8A1>ʵ<EFBFBD><CAB5><EFBFBD><EFBFBD><EFBFBD>Ͳ<EFBFBD><CDB2><EFBFBD><EFBFBD>ڣ<EFBFBD><DAA3><EFBFBD><EFBFBD>Զ<EFBFBD><D4B6><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>͵<EFBFBD>ʵ<EFBFBD><CAB5><EFBFBD><EFBFBD></remarks>
|
|
|
|
|
|
public static object Get(Type instanceType, int stackLayer = 0)
|
|
|
|
|
|
{
|
|
|
|
|
|
foreach (object obj in s_GameFrameworkModules)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
if (obj.GetType() == instanceType)
|
|
|
|
|
|
{
|
|
|
|
|
|
return obj;
|
|
|
|
|
|
}
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2025-11-20 16:17:10 +08:00
|
|
|
|
return Create(instanceType, stackLayer + 1);
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
2025-11-20 16:17:10 +08:00
|
|
|
|
/// <20>Ƿ<EFBFBD><C7B7><EFBFBD><EFBFBD><EFBFBD>ʵ<EFBFBD><CAB5>
|
2025-11-13 16:39:25 +08:00
|
|
|
|
/// </summary>
|
2025-11-20 16:17:10 +08:00
|
|
|
|
/// <param name="type">Ҫ<><D2AA><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ʵ<EFBFBD><CAB5><EFBFBD><EFBFBD><EFBFBD><EFBFBD></param>
|
|
|
|
|
|
/// <returns>ʵ<><CAB5><EFBFBD>Ƿ<EFBFBD><C7B7><EFBFBD><EFBFBD><EFBFBD></returns>
|
|
|
|
|
|
public static bool Contains(Type type)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
foreach (object obj in s_GameFrameworkModules)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
if (obj.GetType() == type)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
return true;
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|
2025-11-20 16:17:10 +08:00
|
|
|
|
return false;
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
|
/// <20><>ȡ<EFBFBD><C8A1>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>ģ<EFBFBD>顣
|
|
|
|
|
|
/// </summary>
|
|
|
|
|
|
/// <typeparam name="T">Ҫ<><D2AA>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>ģ<EFBFBD><C4A3><EFBFBD><EFBFBD><EFBFBD>͡<EFBFBD></typeparam>
|
|
|
|
|
|
/// <returns>Ҫ<><D2AA>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>ģ<EFBFBD>顣</returns>
|
|
|
|
|
|
/// <remarks><3E><><EFBFBD><EFBFBD>Ҫ<EFBFBD><D2AA>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>ģ<EFBFBD>鲻<EFBFBD><E9B2BB><EFBFBD>ڣ<EFBFBD><DAA3><EFBFBD><EFBFBD>Զ<EFBFBD><D4B6><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>ģ<EFBFBD>顣</remarks>
|
|
|
|
|
|
public static T GetModule<T>() where T : GameModule
|
|
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
return (T)Get(typeof(T));
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
|
/// <20>رղ<D8B1><D5B2><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>ģ<EFBFBD>顣
|
|
|
|
|
|
/// </summary>
|
|
|
|
|
|
public static void Shutdown()
|
|
|
|
|
|
{
|
|
|
|
|
|
for (var current = s_GameFrameworkModules.Last; current != null; current = current.Previous)
|
|
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
if (current.Value is GameModule module)
|
|
|
|
|
|
module.Shutdown();
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
s_GameFrameworkModules.Clear();
|
|
|
|
|
|
ReferencePool.ClearAll();
|
|
|
|
|
|
Utility.Marshal.FreeCachedHGlobal();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
|
/// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϸ<EFBFBD><CFB7><EFBFBD><EFBFBD>ģ<EFBFBD><C4A3><EFBFBD><EFBFBD>ѯ<EFBFBD><D1AF>
|
|
|
|
|
|
/// </summary>
|
|
|
|
|
|
/// <param name="elapseSeconds"><3E><EFBFBD><DFBC><EFBFBD><EFBFBD><EFBFBD>ʱ<EFBFBD>䣬<EFBFBD><E4A3AC><EFBFBD><EFBFBD>Ϊ<EFBFBD><CEAA>λ<EFBFBD><CEBB></param>
|
|
|
|
|
|
/// <param name="realElapseSeconds"><3E><>ʵ<EFBFBD><CAB5><EFBFBD><EFBFBD>ʱ<EFBFBD>䣬<EFBFBD><E4A3AC><EFBFBD><EFBFBD>Ϊ<EFBFBD><CEAA>λ<EFBFBD><CEBB></param>
|
|
|
|
|
|
public static void Update(float elapseSeconds, float realElapseSeconds)
|
|
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
foreach (object obj in s_GameFrameworkModules)
|
2025-11-13 16:39:25 +08:00
|
|
|
|
{
|
2025-11-20 16:17:10 +08:00
|
|
|
|
if (obj is GameModule module)
|
|
|
|
|
|
module.Update(elapseSeconds, realElapseSeconds);
|
2025-11-13 16:39:25 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|