// 
// Decompiled by Procyon v0.6.0
// 

package com.hypixel.hytale.component;

import com.hypixel.hytale.component.event.WorldEventType;
import com.hypixel.hytale.component.event.EntityEventType;
import com.hypixel.hytale.component.system.EcsEvent;
import com.hypixel.hytale.component.system.ISystem;
import com.hypixel.hytale.component.spatial.SpatialResource;
import com.hypixel.hytale.component.spatial.SpatialStructure;
import com.hypixel.hytale.codec.builder.BuilderCodec;
import java.util.function.Supplier;
import javax.annotation.Nonnull;
import com.hypixel.hytale.function.consumer.BooleanConsumer;
import java.util.List;

public class ComponentRegistryProxy<ECS_TYPE> implements IComponentRegistry<ECS_TYPE>
{
    private final ComponentRegistry<ECS_TYPE> registry;
    private final List<BooleanConsumer> unregister;
    
    public ComponentRegistryProxy(final List<BooleanConsumer> registrations, final ComponentRegistry<ECS_TYPE> registry) {
        this.unregister = registrations;
        this.registry = registry;
    }
    
    public void shutdown() {
    }
    
    @Nonnull
    @Override
    public <T extends Component<ECS_TYPE>> ComponentType<ECS_TYPE, T> registerComponent(@Nonnull final Class<? super T> tClass, @Nonnull final Supplier<T> supplier) {
        return this.registerComponentType((ComponentType<ECS_TYPE, T>)this.registry.registerComponent((Class<? super T>)tClass, (Supplier<T>)supplier));
    }
    
    @Nonnull
    @Override
    public <T extends Component<ECS_TYPE>> ComponentType<ECS_TYPE, T> registerComponent(@Nonnull final Class<? super T> tClass, @Nonnull final String id, @Nonnull final BuilderCodec<T> codec) {
        return this.registerComponentType((ComponentType<ECS_TYPE, T>)this.registry.registerComponent((Class<? super T>)tClass, id, (BuilderCodec<T>)codec));
    }
    
    @Deprecated(forRemoval = true)
    @Nonnull
    public <T extends Component<ECS_TYPE>> ComponentType<ECS_TYPE, T> registerComponent(@Nonnull final Class<? super T> tClass, @Nonnull final String id, @Nonnull final BuilderCodec<T> codec, final boolean skipValidation) {
        return this.registerComponentType((ComponentType<ECS_TYPE, T>)this.registry.registerComponent((Class<? super T>)tClass, id, (BuilderCodec<T>)codec, skipValidation));
    }
    
    @Nonnull
    @Override
    public <T extends Resource<ECS_TYPE>> ResourceType<ECS_TYPE, T> registerResource(@Nonnull final Class<? super T> tClass, @Nonnull final Supplier<T> supplier) {
        return this.registerResourceType((ResourceType<ECS_TYPE, T>)this.registry.registerResource((Class<? super T>)tClass, (Supplier<T>)supplier));
    }
    
    @Nonnull
    @Override
    public <T extends Resource<ECS_TYPE>> ResourceType<ECS_TYPE, T> registerResource(@Nonnull final Class<? super T> tClass, @Nonnull final String id, @Nonnull final BuilderCodec<T> codec) {
        return this.registerResourceType((ResourceType<ECS_TYPE, T>)this.registry.registerResource((Class<? super T>)tClass, id, (BuilderCodec<T>)codec));
    }
    
    @Nonnull
    @Override
    public ResourceType<ECS_TYPE, SpatialResource<Ref<ECS_TYPE>, ECS_TYPE>> registerSpatialResource(@Nonnull final Supplier<SpatialStructure<Ref<ECS_TYPE>>> supplier) {
        return this.registerResourceType(this.registry.registerSpatialResource(supplier));
    }
    
    @Nonnull
    @Override
    public <T extends ISystem<ECS_TYPE>> SystemType<ECS_TYPE, T> registerSystemType(@Nonnull final Class<? super T> systemTypeClass) {
        return this.registerSystemType(this.registry.registerSystemType(systemTypeClass));
    }
    
    @Nonnull
    @Override
    public <T extends EcsEvent> EntityEventType<ECS_TYPE, T> registerEntityEventType(@Nonnull final Class<? super T> eventTypeClass) {
        return this.registerEntityEventType(this.registry.registerEntityEventType(eventTypeClass));
    }
    
    @Nonnull
    @Override
    public <T extends EcsEvent> WorldEventType<ECS_TYPE, T> registerWorldEventType(@Nonnull final Class<? super T> eventTypeClass) {
        return this.registerWorldEventType(this.registry.registerWorldEventType(eventTypeClass));
    }
    
    @Nonnull
    @Override
    public SystemGroup<ECS_TYPE> registerSystemGroup() {
        return this.registerSystemGroup(this.registry.registerSystemGroup());
    }
    
    @Override
    public void registerSystem(@Nonnull final ISystem<ECS_TYPE> system) {
        final Class<? extends ISystem<ECS_TYPE>> systemClass = system.getClass();
        this.registry.registerSystem(system);
        this.unregister.add(shutdown -> {
            if (!shutdown) {
                if (this.registry.hasSystemClass((Class<ISystem>)systemClass)) {
                    this.registry.unregisterSystem(systemClass);
                }
            }
        });
    }
    
    @Deprecated(forRemoval = true)
    public void registerSystem(@Nonnull final ISystem<ECS_TYPE> system, final boolean bypassClassCheck) {
        final Class<? extends ISystem<ECS_TYPE>> systemClass = system.getClass();
        this.registry.registerSystem(system, bypassClassCheck);
        this.unregister.add(shutdown -> {
            if (!shutdown) {
                if (this.registry.hasSystemClass((Class<ISystem>)systemClass)) {
                    this.registry.unregisterSystem(systemClass);
                }
            }
        });
    }
    
    @Nonnull
    private <T extends Component<ECS_TYPE>> ComponentType<ECS_TYPE, T> registerComponentType(@Nonnull final ComponentType<ECS_TYPE, T> componentType) {
        this.unregister.add(shutdown -> {
            if (shutdown) {
                return;
            }
            else {
                if (componentType.isValid()) {
                    this.registry.unregisterComponent((ComponentType<ECS_TYPE, Component>)componentType);
                }
                return;
            }
        });
        return componentType;
    }
    
    @Nonnull
    private <T extends Resource<ECS_TYPE>> ResourceType<ECS_TYPE, T> registerResourceType(@Nonnull final ResourceType<ECS_TYPE, T> componentType) {
        this.unregister.add(shutdown -> {
            if (shutdown) {
                return;
            }
            else {
                if (componentType.isValid()) {
                    this.registry.unregisterResource((ResourceType<ECS_TYPE, Resource>)componentType);
                }
                return;
            }
        });
        return componentType;
    }
    
    @Nonnull
    private <T extends ISystem<ECS_TYPE>> SystemType<ECS_TYPE, T> registerSystemType(@Nonnull final SystemType<ECS_TYPE, T> systemType) {
        this.unregister.add(shutdown -> {
            if (shutdown) {
                return;
            }
            else {
                if (systemType.isValid()) {
                    this.registry.unregisterSystemType((SystemType<ECS_TYPE, ISystem>)systemType);
                }
                return;
            }
        });
        return systemType;
    }
    
    @Nonnull
    private <T extends EcsEvent> EntityEventType<ECS_TYPE, T> registerEntityEventType(@Nonnull final EntityEventType<ECS_TYPE, T> eventType) {
        this.unregister.add(shutdown -> {
            if (shutdown) {
                return;
            }
            else {
                if (eventType.isValid()) {
                    this.registry.unregisterEntityEventType((EntityEventType<ECS_TYPE, EcsEvent>)eventType);
                }
                return;
            }
        });
        return eventType;
    }
    
    @Nonnull
    private <T extends EcsEvent> WorldEventType<ECS_TYPE, T> registerWorldEventType(@Nonnull final WorldEventType<ECS_TYPE, T> eventType) {
        this.unregister.add(shutdown -> {
            if (shutdown) {
                return;
            }
            else {
                if (eventType.isValid()) {
                    this.registry.unregisterWorldEventType((WorldEventType<ECS_TYPE, EcsEvent>)eventType);
                }
                return;
            }
        });
        return eventType;
    }
    
    @Nonnull
    private SystemGroup<ECS_TYPE> registerSystemGroup(@Nonnull final SystemGroup<ECS_TYPE> systemGroup) {
        this.unregister.add(shutdown -> {
            if (shutdown) {
                return;
            }
            else {
                if (systemGroup.isValid()) {
                    this.registry.unregisterSystemGroup(systemGroup);
                }
                return;
            }
        });
        return systemGroup;
    }
}
