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

package com.hypixel.hytale.server.npc.corecomponents.items;

import com.hypixel.hytale.server.core.inventory.ItemStack;
import com.hypixel.hytale.math.vector.Vector3d;
import com.hypixel.hytale.server.npc.util.InventoryHelper;
import com.hypixel.hytale.server.core.modules.entity.item.ItemComponent;
import com.hypixel.hytale.server.npc.util.NPCPhysicsMath;
import com.hypixel.hytale.server.npc.sensorinfo.InfoProvider;
import com.hypixel.hytale.component.ComponentAccessor;
import com.hypixel.hytale.server.core.modules.entity.component.HeadRotation;
import com.hypixel.hytale.component.Store;
import com.hypixel.hytale.component.Ref;
import com.hypixel.hytale.server.npc.role.Role;
import com.hypixel.hytale.server.npc.corecomponents.builders.BuilderSensorBase;
import com.hypixel.hytale.server.npc.asset.builder.BuilderSupport;
import com.hypixel.hytale.server.npc.corecomponents.items.builders.BuilderSensorDroppedItem;
import com.hypixel.hytale.server.npc.sensorinfo.EntityPositionProvider;
import javax.annotation.Nonnull;
import com.hypixel.hytale.server.core.asset.type.attitude.Attitude;
import java.util.EnumSet;
import javax.annotation.Nullable;
import java.util.List;
import com.hypixel.hytale.server.core.modules.entity.component.TransformComponent;
import com.hypixel.hytale.server.core.universe.world.storage.EntityStore;
import com.hypixel.hytale.component.ComponentType;
import com.hypixel.hytale.server.npc.corecomponents.SensorBase;

public class SensorDroppedItem extends SensorBase
{
    protected static final ComponentType<EntityStore, TransformComponent> TRANSFORM_COMPONENT_TYPE;
    @Nullable
    protected final List<String> items;
    @Nonnull
    protected final EnumSet<Attitude> attitudes;
    protected final double range;
    protected final float viewCone;
    protected final boolean hasLineOfSight;
    protected float heading;
    protected final EntityPositionProvider positionProvider;
    
    public SensorDroppedItem(@Nonnull final BuilderSensorDroppedItem builder, @Nonnull final BuilderSupport support) {
        super(builder);
        this.positionProvider = new EntityPositionProvider();
        final String[] itemArray = builder.getItems(support);
        this.items = ((itemArray != null) ? List.of(itemArray) : null);
        this.attitudes = builder.getAttitudes(support);
        this.range = builder.getRange(support);
        this.viewCone = builder.getViewSectorRadians(support);
        this.hasLineOfSight = builder.getHasLineOfSight(support);
    }
    
    @Override
    public void registerWithSupport(@Nonnull final Role role) {
        role.getPositionCache().requireDroppedItemDistance(this.range);
    }
    
    @Override
    public boolean matches(@Nonnull final Ref<EntityStore> ref, @Nonnull final Role role, final double dt, @Nonnull final Store<EntityStore> store) {
        if (!super.matches(ref, role, dt, store)) {
            this.positionProvider.clear();
            return false;
        }
        final HeadRotation headRotationComponent = store.getComponent(ref, HeadRotation.getComponentType());
        assert headRotationComponent != null;
        this.heading = headRotationComponent.getRotation().getYaw();
        final Ref<EntityStore> droppedItem = role.getPositionCache().getClosestDroppedItemInRange(ref, 0.0, this.range, (sensorDroppedItem, itemRef, role1, componentAccessor) -> sensorDroppedItem.filterItem(ref, itemRef, role1, componentAccessor), role, this, store);
        if (droppedItem == null) {
            this.positionProvider.clear();
            return false;
        }
        this.positionProvider.setTarget(droppedItem, store);
        return true;
    }
    
    @Override
    public InfoProvider getSensorInfo() {
        return this.positionProvider;
    }
    
    protected boolean filterItem(@Nonnull final Ref<EntityStore> ref, @Nonnull final Ref<EntityStore> itemRef, @Nonnull final Role role, @Nonnull final ComponentAccessor<EntityStore> componentAccessor) {
        if (!itemRef.isValid()) {
            return false;
        }
        if (this.viewCone > 0.0f) {
            final TransformComponent selfTransformComponent = componentAccessor.getComponent(ref, SensorDroppedItem.TRANSFORM_COMPONENT_TYPE);
            assert selfTransformComponent != null;
            final Vector3d selfPosition = selfTransformComponent.getPosition();
            final TransformComponent itemTransformComponent = componentAccessor.getComponent(itemRef, SensorDroppedItem.TRANSFORM_COMPONENT_TYPE);
            assert itemTransformComponent != null;
            final Vector3d itemPosition = itemTransformComponent.getPosition();
            if (!NPCPhysicsMath.inViewSector(selfPosition.getX(), selfPosition.getZ(), this.heading, this.viewCone, itemPosition.getX(), itemPosition.getZ())) {
                return false;
            }
        }
        if (this.hasLineOfSight && !role.getPositionCache().hasLineOfSight(ref, itemRef, componentAccessor)) {
            return false;
        }
        if (this.items == null && this.attitudes.isEmpty()) {
            return true;
        }
        final ItemComponent itemComponent = componentAccessor.getComponent(itemRef, ItemComponent.getComponentType());
        assert itemComponent != null;
        final ItemStack itemStack = itemComponent.getItemStack();
        if (InventoryHelper.matchesItem(this.items, itemStack)) {
            return true;
        }
        final Attitude attitude = role.getWorldSupport().getItemAttitude(itemStack);
        return attitude != null && this.attitudes.contains(attitude);
    }
    
    static {
        TRANSFORM_COMPONENT_TYPE = TransformComponent.getComponentType();
    }
}
