Всем привет. Решил написать свой простой Di Container. Пока что чисто на MonoBehavior. Я могу раздавать зависимости методам которые помеченные моим атрибутом. Лист хранит привязки. Теперь мне нужно получить все MonoBehaviour на сцене что бы раздать им зависимости. Как это сделать ? Понятно что все эти объекты можно найти через find. Но сам unity должен хранить список всех MonoBehavior объектов что бы работать с ними в режиме плей мода
public class Container : MonoBehaviour
{
[SerializeField] private List<MonoBehaviour> _containerList;
private const BindingFlags FLAGS = BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance;
private void Awake()
{
InjectDependencies();
}
private void InjectDependencies()
{
foreach (var item in _containerList)
{
InjectAll(item);
}
}
private void InjectAll(MonoBehaviour target)
{
var typeTarget = target.GetType();
var methods = typeTarget.GetMethods(FLAGS).Where(method => method.IsDefined(typeof(Inject))).ToArray();
InjectAllMethods(target, methods);
}
private void InjectAllMethods(MonoBehaviour target, IEnumerable<MethodInfo> methodsInfo)
{
foreach (var methodInfo in methodsInfo)
{
InjectMethod(target, methodInfo);
}
}
private void InjectMethod(MonoBehaviour target, MethodBase methodInfo)
{
var parametersInfo = methodInfo.GetParameters();
var parameters = new object[parametersInfo.Length];
var index = 0;
foreach (var parameterInfo in parametersInfo)
{
if (TryGetDependencyByType(parameterInfo.ParameterType, out var foundDependency))
{
parameters[index] = foundDependency;
index++;
}
else
{
return;
}
}
methodInfo?.Invoke(target, parameters);
}
private bool TryGetDependencyByType(Type type, out MonoBehaviour dependency)
{
foreach (var item in _containerList)
{
if (item.GetType() == type)
{
dependency = item;
return true;
}
}
dependency = null;
return false;
}
}
[AttributeUsage(AttributeTargets.Method)]
public class Inject : Attribute
{
}