local SDKManager = {
	startLoginTime = 0
}

-- 新版本SDK部分 ********************************************************

SDKManager.BF_LOGIN_TYPE = {
	NONE = 0,
	TOKEN = 1,
	GUEST = 2,
	FACEBOOK = 3,
	TEST = 4,
	GOOGLE = 5,
	APPLE = 6
}

SDKManager.BF_LOGIN_RESULT = {
	Success = 0, -- 成功
	TokenInvalid = 100, -- token失效
	NotAccount = 101, -- 账号不存在
	NotBinding = 102, -- 绑定失败
	Data = 103, -- 数据错误
	RepeatBinding = 104, -- 重复绑定
	BindOtherAccount = 105, -- 已绑定其他账号
	CheckToken = 106, -- 检查口令失败
}

-- 用于LoginReq
SDKManager.LOGIN_TYPE = {
	[0] = "none",
	[1] = "token",
	[2] = "guest", -- 游客
	[3] = "facebook",
	[4] = "test",
	[5] = "google",
	[6] = "apple",
}

-- 支付方式
SDKManager.PAY_TYPE = {
	NONE = 0,
	GOOGLE = 1,
	APPLE = 2,
	DEBUG = 10,
	DEPRECATED_APPLE = 11,
}

local PAY_TYPE_IN_APP = "inapp"
local PAY_TYPE_SUBS = "subs"

local SDKPayMgr
if CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.Android then
	SDKPayMgr = require "app/common/sdk_pay_google_manager"
elseif CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.IPhonePlayer then
	SDKPayMgr = require "app/common/sdk_pay_ios_manager"
else
	SDKPayMgr = require "app/common/sdk_pay_default_manager"
end

function SDKManager:init()
	Logger.logHighlight("SDK INIT ---------------")

	-- 标记状态
	self.isLogining = false
	self.isLogouting = false

	-- lazy init
	local SDKMgr = CS.BF.BFMain.Instance.SDKMgr
	self:initPay()
	self:initPayListener()
	-- 初始化AF的广告回传SDK
	CS.BF.BFMain.Instance.SDKMgr.BFThirdReportSDKMgr:InitAppsFlyerAdRevenue()
	self:initAdsListener()

	-- 拿到firebasetoken
	self:initFireBaseToken()
end

-- 支付相关接口 ********************************************************************** 开始
function SDKManager:initPay()
	SDKPayMgr:init()
end

function SDKManager:initPayListener()
	-- 设置支付回调，平时支付走正常回调，如果延迟到账则走延迟到账的回调
	if not SDKPayMgr:needInit() then
		return
	end
	if self.paySid then
		SchedulerManager:unscheduleGlobal(self.paySid)
		self.paySid = nil
	end
	self.paySid = SchedulerManager:performWithDelayGlobal(function()
		self:initPayListener()
	end, 5)
	SDKPayMgr:initPay(function()
		if self.paySid then
			SchedulerManager:unscheduleGlobal(self.paySid)
			self.paySid = nil
		end
		self:queryProducePrice()
	end)
end

function SDKManager:queryProducePrice()
	if self.priceSid then
		SchedulerManager:unscheduleGlobal(self.priceSid)
		self.priceSid = nil
	end
	Logger.log("queryProducePrice")
	if SDKPayMgr:gotProduct() then
		return
	end
	local products = SDKPayMgr:queryProducePrice() or {}
	if #products <= 0 then
		self.priceSid = SchedulerManager:performWithDelayGlobal(function()
			self:queryProducePrice()
		end, 5)
	end
end

-- 查询付费产品信息
function SDKManager:queryProducts(callback)
	SDKPayMgr:queryProducts(callback)
end

-- 处理未完成的订单
function SDKManager:doUncompleteOrder(callback, productId)
	SDKPayMgr:doUncompleteOrder(callback, productId)
end

-- sdk接口 得到特定商品的price
function SDKManager:getProductPrice(skuId)
	return SDKPayMgr:getProductPrice(skuId)
end

-- sdk接口 得到特定商品的priceAmountMicros
function SDKManager:getProductPriceAmountMicros(skuId)
	return SDKPayMgr:getProductPriceAmountMicros(skuId)
end

-- sdk接口 得到特定商品的currency_code
function SDKManager:getPriceCurrencyCode(skuId)
	return SDKPayMgr:getPriceCurrencyCode(skuId)
end

-- 获取支付方式,目前只有google支付
function SDKManager:getSDKPayType()
	return SDKPayMgr:getSDKPayType()
end

function SDKManager:getIsSupportSDKPay()
	return SDKPayMgr:getIsSupportSDKPay()
end

-- 获取支付参数
function SDKManager:getPurchaseArgs(purchaseToken, uuid, channelOrderId, productId)
	return SDKPayMgr:getPurchaseArgs(purchaseToken, uuid, channelOrderId, productId)
end

-- sdk将已完成的订单消耗掉
function SDKManager:consumePurchase(token, callback)
	SDKPayMgr:consumePurchase(token, callback)
end

-- 检查是否可以支付
function SDKManager:checkPay(productId, callback)
	if not productId or not Platform:getIsPublishChannel() or not SDKManager:getIsSupportSDKPay() then -- 没有productId、非正式渠道、不支持sdk支付的直接返回可支付
		callback(0)
		return
	end

	SDKPayMgr:checkPay(productId, callback)
end

-- 支付
function SDKManager:pay(productId, orderId, rechargeId, giftType, purchaseType, giftId, callback)
	SDKPayMgr:pay(productId, orderId, rechargeId, giftType, purchaseType, giftId, callback)
end

function SDKManager:doUncompletePay(callback)
	SDKPayMgr:doUncompletePay(callback)
end

function SDKManager:getIosPayInfo(transactionID)
	if SDKPayMgr.getIosPayInfo then
		return SDKPayMgr:getIosPayInfo(transactionID)
	end
end

function SDKManager:delIosPayInfo(transactionID)
	if SDKPayMgr.delIosPayInfo then
		return SDKPayMgr:delIosPayInfo(transactionID)
	end
end

function SDKManager:delIosOrder(productId)
	if SDKPayMgr.delIosOrder then
		return SDKPayMgr:delIosOrder(productId)
	end
end

-- 支付相关接口 ********************************************************************** 结束

-- 获取设备语言
function SDKManager:getLanguage()
	return CS.BF.BFMain.Instance.SDKMgr:GetLanguage()
end

-- 获取设备时区
function SDKManager:getTimeZone()
	return CS.BF.BFMain.Instance.SDKMgr:GetTimeZone()
end

function SDKManager:initFireBaseToken()
	CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:GetFirebaseToken(function(token)
		self.firebaseToken = token
		CS.BF.BFMain.Instance.SDKMgr.BFThirdReportSDKMgr:AdjustSetDeviceToken(token)
	end)
end

function SDKManager:doNextFrame(callback)
	SchedulerManager:performWithDelayGlobal(callback, 0)
end

---  广告
function SDKManager:isAdLoaded()
	if CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.Android then
		return CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr.AdLoaded
	elseif CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.IPhonePlayer then
		return CS.AdManager.Instance:IsRewardedAdReady()
	elseif EDITOR_MODE then
		return true
	end
	return false
end

function SDKManager:tryLoadRewardedAdDelay()
	if self.adDelaySid then
		SchedulerManager:unscheduleGlobal(self.adDelaySid)
		self.adDelaySid = nil
	end
	self.adDelaySid = SchedulerManager:performWithDelayGlobal(function()
		self.adDelaySid = nil
		CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr:TryLoadRewardedAd()
	end, 5)
end

function SDKManager:initAdsListener()
	if CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.Android then
		CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr:SetAdShowCallback(function(code)
			-- code 为0 表示广告播放成功
			if code == 0 then
				BIReport:postAdPlaySuccess(self.adsClickType)
			else
				self:tryLoadRewardedAdDelay()
			end
		end)
		CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr:SetAdLoadedCallback(function(code)
			-- code 为0 表示广告加载成功
			if code ~= 0 then
				self:tryLoadRewardedAdDelay()
			end
		end)
		CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr:SetAdEarnedRewardCallback(function(code, result)
			if self.adCallback then
				if DataManager.PlayerData then
					DataManager.PlayerData:addAdCount()
					local data = {}
					data.ads_num = DataManager.PlayerData:getAdCount()
					CS.ThinkingAnalytics.ThinkingAnalyticsAPI.UserSet(data)
				end
				self:adRewradAd()
				self.adCallback()
				BIReport:postAdRewardGet(self.adsClickType)
				self.adsClickType = nil
				self.adCallback = nil
			end
		end)
        CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr:SetAdRevenuePaidEventCallback(function (result)
            if result and result ~= GConst.EMPTY_STRING then
                BIReport:postIronSourceAdRevenue(result)
            end
        end)
	elseif CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.IPhonePlayer then
		-- 初始化一下
		local adManager = CS.AdManager.Instance
        adManager:SetAdRevenuePaidEventCallback(function (result)
            if result and result ~= GConst.EMPTY_STRING then
                BIReport:postAppLovinAdRevenue(result)
            end
        end)
	end
end

function SDKManager:showFullScreenAds(adsClickType, adCallback)
	if EDITOR_MODE then
		if not adsClickType then
			local params = {
				content = "SDKManager showFullScreenAds has no adsClickType",
				boxType = GConst.MESSAGE_BOX_TYPE.MB_OK,
				okText = I18N:getGlobalText(I18N.GlobalConst.BTN_TEXT_OK),
			}
			GFunc.showMessageBox(params)
			Logger.log("SDKManager showFullScreenAds has no adsClickType")
		end
	end

	BIReport:postAdClick(adsClickType)
	if EDITOR_MODE then
		if DataManager.PlayerData then
			DataManager.PlayerData:addAdCount()
			local data = {}
			data.ads_num = DataManager.PlayerData:getAdCount()
			CS.ThinkingAnalytics.ThinkingAnalyticsAPI.UserSet(data)
		end
		self:adRewradAd()
		if adCallback then
			adCallback()
		end
		return true
	end
	if NetManager:isNotReachable() then
		-- 没有网
		GFunc.showToast(I18N:getGlobalText(I18N.GlobalConst.NO_NETWORK))
		return false
	end
	if NetManager:getIsBusy() then
		GFunc.showToast(I18N:getGlobalText(I18N.GlobalConst.NETWORK_ERROE_1))
		return false
	end
	-- if DataManager.MallActData:skipAd() then
	-- 	self:adRewradAd(true)
	-- 	if adCallback then
	-- 		adCallback()
	-- 	end
	-- 	return true
	-- end
	if CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.Android then
		if not CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr.AdLoaded then
			GFunc.showToast(I18N:getGlobalText(I18N.GlobalConst.NO_ADS))
			return false
		end
		CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr:SetAdPlacement(adsClickType)
		CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr.AdLoaded = false
		self.adCallback = adCallback
		self.adsClickType = adsClickType
		CS.BF.BFMain.Instance.SDKMgr.BFIronSourceSDKMgr:ShowFullScreenAds()
		return true
	elseif CS.UnityEngine.Application.platform == CS.UnityEngine.RuntimePlatform.IPhonePlayer then
		if not CS.AdManager.Instance:IsRewardedAdReady() then
			GFunc.showToast(I18N:getGlobalText(I18N.GlobalConst.NO_ADS))
			return false
		end
		self.adsClickType = adsClickType
		BIReport:postAdPlaySuccess(self.adsClickType)
		CS.AdManager.Instance:ShowRewardedAd(function(code)
			if code == 0 then
				if DataManager.PlayerData then
					DataManager.PlayerData:addAdCount()
					local data = {}
					data.ads_num = DataManager.PlayerData:getAdCount()
					CS.ThinkingAnalytics.ThinkingAnalyticsAPI.UserSet(data)
				end
				self:adRewradAd()
				if adCallback then
					adCallback()
				end
				BIReport:postAdRewardGet(self.adsClickType)
				self.adsClickType = nil
			end
		end)
		return true
	end
end

function SDKManager:adRewradAd(noReport)
	ModuleManager.TaskManager:addTaskProgress(GConst.TaskConst.TASK_TYPE.X_WATCH_AD)
	if not noReport then
		BIReport:postAdEvent()
	end
end

function SDKManager:getServerList(callback)
	local postData = {
		project_id = "c1",
		bundle_id = Platform:getIdentifier(),
		version = Platform:getClientVersion(),
		device_id = DeviceHelper:getDeviceId(),
		language = I18N:getLanguageAndArea(),
		env = "release",-- 暂时写死
	}
	local loginCenterUrl = CS.BF.BFPlatform.GetLoginCenterURL()
	loginCenterUrl = loginCenterUrl .. "?platform=" .. CS.System.Uri.EscapeDataString(Platform:getPlatformStr())
	-- lua这边直接构建好参数
	for k, v in pairs(postData) do
		loginCenterUrl = loginCenterUrl .. "&" .. k .. "=" .. CS.System.Uri.EscapeDataString(v)
	end
	local guid = CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:GetNewPlayerGuid()
    loginCenterUrl = loginCenterUrl .. "&random=" .. CS.System.Uri.EscapeDataString(guid)
	CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:SetLuaServerListCallback(function(isSuccess, data)
		if callback then
			callback(isSuccess, data)
		end
	end)
	CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:GetServerList(loginCenterUrl)
end

function SDKManager:_login(callback, loginType)
    CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:SetLuaLoginCallback(callback)
    CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:Login(loginType)
end

function SDKManager:login(callback, loginType)
    self:logout(function()
        if self.isLogining then -- 正在登陆中
            Logger.log("三方当前正在登陆中")
            return
        end
        self.isLogining = true
        self:_login(function(code, msg)
			Logger.log("login finish:%s %s", code, msg)
            if code == SDKManager.BF_LOGIN_RESULT.Success then
                if not msg then
                    self.isLogining = false
                    return
                end
                local msgTab = json.decode(msg)
                if msgTab == nil or type(msgTab) ~= "table" then
                    self.isLogining = false
                    return
                end
                local loginResult = json.decode(msgTab.msg)
                if loginResult == nil or type(loginResult) ~= "table" then
                    self.isLogining = false
                    return
                end
                local userId = loginResult.UserId
                local token = loginResult.Token
                local params = {}
                if loginType == SDKManager.BF_LOGIN_TYPE.APPLE then
                    params = {
						type = "apple",
                        id = tostring(userId),
                        token = tostring(token)
                    }
                elseif loginType == SDKManager.BF_LOGIN_TYPE.GOOGLE then
                    params = {
						type = "google",
                        id = tostring(userId),
                        token = tostring(token)
                    }
                end
                if callback then
                    callback(params)
                end
            end
            self.isLogining = false
        end, loginType)
    end, loginType)
end

function SDKManager:_logout(callback, loginType)
    if loginType == SDKManager.BF_LOGIN_TYPE.FACEBOOK or loginType == SDKManager.BF_LOGIN_TYPE.GOOGLE then
        CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:SetLuaLogoutCallback(callback)
        CS.BF.BFMain.Instance.SDKMgr.BFLoginSDKMgr:Logout(loginType)
    else
        if callback then
            callback(SDKManager.BF_LOGIN_RESULT.Success, nil)
        end
    end
end

function SDKManager:logout(callback, loginType)
    if self.isLogouting then -- 正在登出
        Logger.log("当前正在登出中")
        return
    end
    self.isLogouting = true
    self:_logout(function(code, msg)
        if code == SDKManager.BF_LOGIN_RESULT.Success then
            if callback then
                callback()
            end
        else
            if msg and msg ~= "" then
                local jData = json.decode(msg)
                if jData then
                    Logger.logError("登出失败 result:%s  type:%s  msg:%s", code, jData.loginType, jData.msg)
                else
                    Logger.logError("登出失败 result:%s", code)
                end
            else
                Logger.logError("登出失败")
            end
            if callback then
                callback()
            end
        end
        self.isLogouting = false
    end, loginType)
end

return SDKManager
