using UnityEngine;
using UnityEngine.UI;

public sealed class MarketUIFoldPanel : MonoBehaviour, ResourceTradeControlItem.IController
{
    [SerializeField]
    private Text stantionName = null;
    [SerializeField]
    private Button backButton = null;
    [SerializeField]
    private Profile Profile = null;
    [SerializeField]
    private ResourceTradeControlItem[] resourceTradeControls = null;
    [SerializeField]
    private CreditsUICounter creditsCounter = null;
    [SerializeField]
    private SpaceUICounter spaceCounter = null;

    public Player Player => Profile.Player;
    private ITradeProvider tradeAgent = null;

    public void Hide()
    {
        gameObject.SetActive(false);
        tradeAgent = null;
    }

    public void Show(ITradeProvider trader)
    {
        tradeAgent = trader;
        stantionName.text = trader.Name;
        gameObject.SetActive(true);
        UpdateInfo(tradeAgent);
    }

    private void UpdateInfo(ITradeProvider stantion)
    {
        creditsCounter.Show(Player.Credits);
        spaceCounter.Show(Player.StarShip.GetCargoSpace(), Player.StarShip.GetFullSpace());
        UpdateResourceCount(stantion);
    }

    private void UpdateResourceCount(ITradeProvider trader)
    {
        var keys = Profile.Player.EconomyParams.ResourceIds;
        for (int i = 0; i < resourceTradeControls.Length; i++)
        {
            var resourceId = string.Empty;
            if (i < keys.Length)
            {
                resourceId = keys[i];
            }
            var buyCost = trader.GetResourceBuyCost(resourceId);
            var sellCost = trader.GetResourceSellCost(resourceId);
            resourceTradeControls[i].SetResource(
                resourceId,
                trader.Resources[resourceId],
                Player.StarShip.Resources[resourceId],
                Player.GetLastCostRounded(resourceId),
                buyCost, sellCost);
        }
    }

    public void Buy(string resourceId)
    {
        if (tradeAgent.Resources[resourceId] <= 0)
            return;

        var emptyPlace = Player.StarShip.GetEmptySpace();
        if (emptyPlace == 0)
        {
            spaceCounter.ShowNoSpaceEffect();
            return;
        }
        var buyCost = tradeAgent.GetResourceBuyCost(resourceId);
        if (Player.TryBuy(resourceId, buyCost, 1))
        {
            tradeAgent.Resources[resourceId] -= 1;
            UpdateInfo(tradeAgent);
        }
        else
        {
            creditsCounter.ShowNoCreditsEffect();
        }
    }

    public void BuyMax(string resourceId)
    {
        var emptyPlace = Player.StarShip.GetEmptySpace();
        if (emptyPlace == 0)
        {
            spaceCounter.ShowNoSpaceEffect();
            return;
        }
        var buyCost = tradeAgent.GetResourceBuyCost(resourceId);
        var maxUnits = buyCost > 0 ?  Player.Credits / buyCost : 99999; // fix zero cost
        if (maxUnits == 0)
        {
            creditsCounter.ShowNoCreditsEffect();
            return;
        }
        var maxCountOnStantion = tradeAgent.Resources[resourceId];
        var count = Mathf.Min(emptyPlace, maxUnits, maxCountOnStantion);
        if (count == 0)
            return;
        if (Player.TryBuy(resourceId, buyCost, count))
        {
            tradeAgent.Resources[resourceId] -= count;
            UpdateInfo(tradeAgent);
        }
        else
        {
            creditsCounter.ShowNoCreditsEffect();
        }
    }

    public void Sell(string resourceId)
    {
        var sellCost = tradeAgent.GetResourceSellCost(resourceId);
        if (Player.TrySell(resourceId, sellCost, 1))
        {
            tradeAgent.Resources[resourceId] += 1;
            UpdateInfo(tradeAgent);
        }
    }

    public void SellMax(string resourceId)
    {
        var sellCost = tradeAgent.GetResourceSellCost(resourceId);
        var maxUnits = Player.StarShip.Resources[resourceId];
        if (Player.TrySell(resourceId, sellCost, maxUnits))
        {
            tradeAgent.Resources[resourceId] += maxUnits;
            UpdateInfo(tradeAgent);
        }
    }

    private void Start()
    {
        foreach (var control in resourceTradeControls)
        {
            control.Init(this);
        }
        backButton.onClick.AddListener(Hide);
    }

    private void OnDestroy()
    {
        backButton.onClick.AddListener(Hide);
    }

    public void Update()
    {
        if (Input.GetKey(KeyCode.Escape))
        {
            Hide();
        }
    }
}
