#if UNITY_STANDALONE
using System;
using System.Collections.Generic;
using System.Linq;
using _Core;
using Seayoo.ComboSDK.Windows;

namespace _Combo
{
    internal class ComplainManager : Singleton<ComplainManager>
    {
        private string gameId = "";
        private string complainUrl = "";
        private Action<ComboResult<ComplainResult>> complainResult;

        public void Setup(string gameId)
        {
            EventSystem.Register(this);
            this.gameId = gameId;
            this.complainUrl = GlobalParameters.Instance.GameComplainUrl;
        }

        public void Complain(ComplainOptions opts, Action<ComboResult<ComplainResult>> action)
        {
            complainResult = action;
            if(string.IsNullOrEmpty(complainUrl))
            {
                var invalidArgumentsError = new InvalidArgumentsError("complain", errorType : InvalidArgumentsErrorType.INVALID_COMPLAIN_URL);
                var error = new InternalError(I18n.T("complain_url_error"), invalidArgumentsError);
                complainResult?.Invoke(ComboResult<ComplainResult>.CreateFail(error));
                return;
            }

            CreateComplainTicket(opts, ticket =>{
                try
                {
                    var url = GetUrl(ticket, opts);
                    Log.I("complain url: " + url);
                    UIController.Instance.ShowWebView(url, WebViewType.Complain, opts.Width, opts.Height, false);
                }
                catch(InternalError error)
                {
                    UIController.Instance.HideLoading();
                    complainResult?.Invoke(ComboResult<ComplainResult>.CreateFail(error));
                }
            });
        }

        private void CreateComplainTicket(ComplainOptions opts, Action<string> callback)
        {
            if(!IdPManager.Instance.GetUser().IsLogin())
            {
                var error = new InternalError(I18n.T("login_required_error"));
                complainResult?.Invoke(ComboResult<ComplainResult>.CreateFail(error));
                return;
            }
            var identityToken = IdPManager.Instance.GetUser().identityToken;

            UIController.Instance.ShowLoading(0.5f);
            ComboClient.CreateComplainTicket(identityToken, opts.TargetType, opts.TargetId, opts.TargetName, opts.ServerId, opts.RoleId, opts.RoleName, opts.Context, result =>{
                if(result.IsSuccess)
                {
                    var ticket = result.Data.ticket;
                    Log.I("CreateComplainTicket success: " + ticket);
                    callback(ticket);
                }
            }, (err) => {
                UIController.Instance.HideLoading();
                complainResult?.Invoke(ComboResult<ComplainResult>.CreateFail(err));
            });
        }

        [EventSystem.BindEvent]
        public void LoadComplainFailed(LoadFailed evt)
        {
            if(evt.webViewType != WebViewType.Complain)
            {
                return;
            }
            var error = new InternalError(I18n.T("complain_open_error"));
            complainResult?.Invoke(ComboResult<ComplainResult>.CreateFail(error));
        }

        [EventSystem.BindEvent]
        public void LoadComplainSuccess(LoadSuccess evt)
        {
            if(evt.webViewType != WebViewType.Complain)
            {
                return;
            }
            complainResult?.Invoke(ComboResult<ComplainResult>.CreateSuccess(new ComplainResult()));
        }

        private string GetUrl(string ticket, ComplainOptions opts)
        { 
            var queryParameters = new Dictionary<string, string>
            {
                { "game_id", gameId },
                { "ticket", ticket },
                { "target_type", opts.TargetType },
                { "target_id", opts.TargetId },
                { "target_name", opts.TargetName},
                { "lang", I18n.GetLanguageCode()}
            };
            if(!string.IsNullOrEmpty(opts.Category))
            {
                queryParameters.Add("category", opts.Category);
            }
            string queryParametersStr = string.Join("&", queryParameters.Select(kv => $"{kv.Key}={kv.Value}"));
            return $"{complainUrl}?{queryParametersStr}";
        }
    }
}
#endif