In Entity Component Systems, an entity holds a relationship to the data that is in components, and then each component is operated on by what can be multiple systems. Each system can depend on many components.
Currently I'm implementing the systems in a base class and doing much of the heavy lifting of finding and coupling the components together to the same entity. A lot of this is done using Generics, and it works quite well.
public abstract class System<T1>: System
where T1: Component
{
public override void Update( long delta )
{
ComponentStorage<Component> componentStorage1 = GetComponentStorageByType<T1>( );
List<Entity> entities = GetEntities( );
if ( componentStorage1 == null )
return;
entities.ForEach( e =>
{
int index = entities.IndexOf( e );
if ( componentStorage1[ index ] == null )
return;
Update( (T1) componentStorage1[ index ], delta );
} );
}
protected abstract void Update( T1 component1, long delta );
}
The inherited classes overrides the method called Update, which I pass instantiated components to through the update method from the storages.
class TestSystem1: System<TestComponent1>
{
protected override void Update( TestComponent1 component1, long delta )
{
Console.WriteLine( $"{component1.Count++}" );
}
}
This works well for systems with only one component. If the system has more than one components, I would have to add another generic Tn for however many components, which means implementing an up to unlimited number of classes.
I've looked into variable number of generic arguments, C++11 has it but C# does not.
I can probably fit reflection to work magic, but until I've exhausted all other options I'd rather not.
Is there a design that can satisfy my needs? I would like it to leave the inherited class the most intact - call an override, protected Update method ( or similar ) and have an already cast components handed to it.