package com.base.appzxhy.ads

import android.app.Activity
import android.content.Context
import android.view.LayoutInflater
import android.view.ViewGroup
import android.widget.FrameLayout
import androidx.annotation.LayoutRes
import com.applovin.sdk.AppLovinMediationProvider
import com.applovin.sdk.AppLovinSdk
import com.applovin.sdk.AppLovinSdkInitializationConfiguration
import com.base.appzxhy.BuildConfig
import com.base.appzxhy.GlobalConfig
import com.base.appzxhy.ads.admob.AdBannerMgr
import com.base.appzxhy.ads.admob.AdInterMgr
import com.base.appzxhy.ads.admob.AdNativeMgr
import com.base.appzxhy.ads.admob.AdOpenMgr
import com.base.appzxhy.ads.admob.AdmobEvent
import com.base.appzxhy.ads.applovin.AdMaxEvent
import com.base.appzxhy.ads.applovin.MaxInsertMgr
import com.base.appzxhy.ads.applovin.MaxNativeMgr
import com.base.appzxhy.ads.applovin.MaxOpenMgr
import com.base.appzxhy.bean.config.AdConfigBean.Companion.adsConfigBean
import com.base.appzxhy.bean.config.ConfigBean.Companion.configBean
import com.base.appzxhy.helper.EventUtils
import com.base.appzxhy.utils.AppPreferences
import com.base.appzxhy.utils.LogEx
import com.base.appzxhy.utils.ToastUtils.toast
import com.google.android.gms.ads.MobileAds
import com.google.android.gms.ads.identifier.AdvertisingIdClient
import com.google.android.gms.ads.initialization.AdapterStatus
import com.google.android.gms.ads.nativead.NativeAdView
import java.util.Collections
import java.util.concurrent.Executors

/**
 * 广告管理类
 */
object AdsMgr {

    private val adOpenMgr by lazy {
        AdOpenMgr()
    }
    private val adInsertMgr by lazy {
        AdInterMgr()
    }

    private val adNativeMgr by lazy {
        AdNativeMgr()
    }

    private val adBannerMgr by lazy {
        AdBannerMgr()
    }

    private val maxOpenMgr by lazy {
        MaxOpenMgr()
    }
    private val maxInsertMgr by lazy {
        MaxInsertMgr()
    }

    private val maxNativeMgr by lazy {
        MaxNativeMgr()
    }

    /**
     * 是否初始化
     */
    var isAdmobInit = false
        private set

    /**
     * 是否初始化
     */
    var isMaxInit = false
        private set


    /**
     * Init 初始化
     *
     * @param context 这里最好是appContext，因为是耗时操作，等它初始化完毕马上加载开屏和插屏广告
     */
    fun init(context: Context) {

        if (configBean.isInBlackList) {
            EventUtils.event("isInBlackList", configBean.isInBlackList.toString())
            return
        }
        initAdmob(context)
        initMax(context)

    }

    private fun initAdmob(context: Context) {
        MobileAds.initialize(context) {
            val readyAdapter = it.adapterStatusMap.entries.find { entry ->
                entry.value.initializationState == AdapterStatus.State.READY
            }
            isAdmobInit = readyAdapter != null
            EventUtils.event("AdmobInit", "AdmobInit")
//            context.toast("admob init")

            if (adsConfigBean.adSwitch) {
                admobInitCallBack?.invoke()
                admobInitCallBack = null
                adOpenMgr.loadAd(context, false, AdmobEvent("openAd", context::class.java.simpleName))
                adInsertMgr.loadAd(context, false, AdmobEvent("interAd", context::class.java.simpleName))
            }
        }

    }

    private fun initMax(context: Context) = kotlin.runCatching {

        val executor = Executors.newSingleThreadExecutor()

        executor.execute {
            val currentGaid = AdvertisingIdClient.getAdvertisingIdInfo(context).id
            AppPreferences.getInstance().getString("gid", currentGaid)

            val build = AppLovinSdkInitializationConfiguration
                .builder(GlobalConfig.KEY_MAX, context)

            build.setMediationProvider(AppLovinMediationProvider.MAX)
            if (BuildConfig.DEBUG) {
                build.testDeviceAdvertisingIds = Collections.singletonList(currentGaid)
            }
            val initConfig = build.build()
            runCatching {
                AppLovinSdk.getInstance(context).initialize(initConfig) {
                    isMaxInit = true
//                maxOpenMgr.loadAd(context)
                    if (!adsConfigBean.adSwitch) {
                        maxInsertMgr.loadAd(context, false, AdMaxEvent("interAd", context::class.java.simpleName))
                        context.toast("max init")
                        maxInitCallBack?.invoke()
                        maxInitCallBack = null
                    }
                }
            }

        }

    }


    private var admobInitCallBack: (() -> Unit)? = null
    private var maxInitCallBack: (() -> Unit)? = null


    /**
     * 展示开屏广告
     *
     * @param activity 当前页面
     * @param showCallBack  展示回调
     */
    fun showOpen(
        activity: Activity,
        isUnLimit: Boolean = false,
        showCallBack: AdsShowCallBack? = null,
    ) {
        if (configBean.isInBlackList) {
            EventUtils.event("isInBlackList", "isInBlackList=${configBean.isInBlackList}")
            return
        }

        val from = activity::class.java.simpleName
        if (adsConfigBean.adSwitch) {
            if (isAdmobInit) {
                adOpenMgr.show(activity, isUnLimit, AdmobEvent("openAd", from), showCallBack)
            } else {
                admobInitCallBack = {
                }
                adOpenMgr.show(activity, isUnLimit, AdmobEvent("openAd", from), showCallBack)
            }
        } else {
            if (isMaxInit) {
                maxOpenMgr.show(activity, isUnLimit, AdMaxEvent("openAd", from), showCallBack)
            } else {
                maxInitCallBack = {
                    maxOpenMgr.show(activity, isUnLimit, AdMaxEvent("openAd", from), showCallBack)
                }
            }
        }

    }

    /**
     * 展示插屏广告
     *
     * @param activity 当前页面
     * @param showCallBack  展示回调
     * @param isUnLimit 是否不受限制 默认false 代表受到限制
     */
    fun showInsert(
        activity: Activity,
        isUnLimit: Boolean = false,
        showCallBack: AdsShowCallBack? = null,
    ) {
        if (configBean.isInBlackList) {
            EventUtils.event("isInBlackList", configBean.isInBlackList.toString())
            return
        }
        LogEx.logDebug("showAd", "adSwitch=${adsConfigBean.adSwitch}")
        val from = activity::class.java.simpleName
        if (adsConfigBean.adSwitch) {
            adInsertMgr.show(activity, isUnLimit, AdmobEvent("interAd", from), showCallBack)
        } else {
            maxInsertMgr.show(activity, isUnLimit, AdMaxEvent("interAd", from), showCallBack)
        }
    }

    /**
     * 展示原生广告
     *
     * @param parent 需要展示原生广告的布局容器
     * @param layout Admob原生根布局必须为 NativeAdView
     */
    fun showNative(
        activity: Activity,
        parent: FrameLayout,
        @LayoutRes layout: Int,
        nativeCallBack: ((Any?) -> Unit)? = null
    ) {
        if (configBean.isInBlackList) {
            EventUtils.event("isInBlackList", configBean.isInBlackList.toString())
            return
        }

        if (!isAdmobInit) return

        val from = activity::class.java.simpleName

        if (adsConfigBean.adSwitch) {

            val nativeView = LayoutInflater.from(parent.context).inflate(layout, parent, false) as NativeAdView
            adNativeMgr.show(AdmobEvent("nativeAd", from), parent, nativeView, nativeCallBack)

        } else {
//            maxNativeMgr.show(AdMaxEvent("nativeAd", "nativeAd"), nativeParent, layout, nativeCallBack)
        }
    }

    fun isNativeShow() = (isAdmobInit && !configBean.isInBlackList) && LimitUtils.isAdShow(AdsType.NATIVE, null)

    /**
     * 展示banner广告
     *
     * @param parent 展示广告的父布局容器
     */
    fun showBanner(parent: ViewGroup, collapsible: Boolean = true, adClose: (() -> Unit)? = null) {
        if (configBean.isInBlackList) {
            EventUtils.event("isInBlackList", configBean.isInBlackList.toString())
            return
        }
        if (adsConfigBean.adSwitch) {
            adBannerMgr.show(parent, collapsible, adClose)
        }
    }
}