package com.secspace.sms.popup

import android.animation.ObjectAnimator
import android.annotation.SuppressLint
import android.content.Context
import android.os.Build
import android.os.Handler
import android.os.Looper
import android.os.Message
import android.util.DisplayMetrics
import android.util.Log
import android.view.*
import android.view.View.OnTouchListener
import android.widget.LinearLayout
import android.widget.TextView
import com.secspace.sms.R
import com.secspace.sms.helpers.Constant


/**
 * Created by 2025/4/7
 * Zhang-Chengbo
 *
 * 描述：自定义弹窗
 */
class MyPushWindow(context: Context, title: String = "", info: String = "") : OnTouchListener {

    private val mContext: Context = context
    private var wm: WindowManager? = null
    private var linearLayout: LinearLayout? = null
    private var downY = 0
    private var mTitle: String = ""
    private var content: String = ""

    private val mHander: Handler = object : Handler(Looper.myLooper()!!) {
        override fun handleMessage(msg: Message) {
            super.handleMessage(msg)
            animDismiss()
        }
    }

    init {
        mTitle = title
        content = info
    }

    /**
     * 动画，从顶部弹出
     */
    @SuppressLint("ObjectAnimatorBinding")
    private fun animShow() {
        //使用动画从顶部弹出
        val animator = ObjectAnimator.ofFloat(linearLayout, "translationY", -linearLayout!!.measuredHeight.toFloat(), 0f)
        animator.duration = 800
        animator.start()
    }

    /**
     * 动画，从顶部收回
     *
     * 不使用动画，会造成动画完成后再移出View 闪烁问题
     */
    @SuppressLint("ObjectAnimatorBinding")
    private fun animDismiss() {
        if (linearLayout == null || linearLayout!!.parent == null) {
            return
        }
        wm!!.removeView(linearLayout)

        /*val animator = ObjectAnimator.ofFloat(linearLayout, "translationY", linearLayout!!.translationY, -linearLayout!!.measuredHeight.toFloat())
        animator.duration = 500
        animator.start()
        animator.addListener(object : AnimatorListenerAdapter() {
            override fun onAnimationEnd(animation: Animator) {
                super.onAnimationEnd(animation)
                //移除HeaderToast  (一定要在动画结束的时候移除,不然下次进来的时候由于wm里边已经有控件了，所以会导致卡死)
                    wm!!.removeView(linearLayout)
            }
        })*/
    }

    /**
     * 向外部暴露显示的方法
     */
    fun show(delayMillis: Long = Constant.DEALTIME) {
        createPopTipsView()
        animShow()
        //3S后自动关闭
        mHander.sendEmptyMessageDelayed(Constant.MIN_RECENTS_THRESHOLD, delayMillis)
    }

    /**
     * 向外部暴露关闭的方法
     */
    fun dismiss() {
        animDismiss()
    }

    /**
     * 视图创建方法
     */
    private fun createPopTipsView() {

        if (linearLayout != null && linearLayout!!.parent != null) {
            wm!!.removeView(linearLayout)
        }

        val popView = View.inflate(mContext, R.layout.popup_tips, null)
        val tvTitle = popView.findViewById<TextView>(R.id.tv_notific_title)
        val tvContent = popView.findViewById<TextView>(R.id.tv_notific_content)
        if (mTitle.isNotEmpty()) {
            tvTitle.text = "来自 $mTitle 的短信"
        } else {
            tvTitle.text = "短信提醒"
        }

        tvContent.text = content.trim()

        //准备Window要添加的View
        linearLayout = LinearLayout(mContext)
        val layoutParams = LinearLayout.LayoutParams(
            LinearLayout.LayoutParams.MATCH_PARENT,
            LinearLayout.LayoutParams.WRAP_CONTENT
        )

        // 设置Touch事件
        linearLayout?.apply {
            this.layoutParams = layoutParams
            setOnTouchListener(this@MyPushWindow)
            addView(popView)
            measure(0, 0)
        }

        // 定义WindowManager 并且将View添加到WindowManagar中去
        wm = mContext.getSystemService(Context.WINDOW_SERVICE) as WindowManager
        val wmParams = WindowManager.LayoutParams().apply {
            flags = (WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL
                or WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
                or WindowManager.LayoutParams.FLAG_FULLSCREEN
                or WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN)

            //这里需要注意，因为不同系统版本策略不一，所以需要根据版本判断设置type，否则会引起崩溃。
            type = if (Build.VERSION.SDK_INT > Build.VERSION_CODES.N_MR1) { //大于android SDK 7.1.1
                WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY
            } else {
                WindowManager.LayoutParams.TYPE_SYSTEM_ALERT
            }

            gravity = Gravity.TOP
            x = 0
            y = 0
            format = -3 // 会影响Toast中的布局消失的时候父控件和子控件消失的时机不一致，比如设置为-1之后就会不同步
            alpha = 1f

            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
                val windowMetrics = wm?.currentWindowMetrics
                windowMetrics?.let {
                    val insets = it.windowInsets.getInsetsIgnoringVisibility(WindowInsets.Type.systemBars())
                    val width: Int = it.bounds.width() - insets.left - insets.right
//                val height: Int = it.bounds.height() - insets.top - insets.bottom
                    //width=1200  height = 2664  DEFAULT_DISPLAY=0
                    this.width = width - Constant.MARSPACE
                }
            } else {
                val metrics = DisplayMetrics()
                wm!!.defaultDisplay.getMetrics(metrics)
                this.width = metrics.widthPixels - Constant.MARSPACE
            }
            this.height = linearLayout!!.measuredHeight
        }

        wm?.addView(linearLayout, wmParams)

    }

    override fun onTouch(v: View?, event: MotionEvent): Boolean {
        when (event.action) {
            MotionEvent.ACTION_DOWN -> {
                downY = event.rawY.toInt()
            }

            MotionEvent.ACTION_MOVE -> {
                val moveY = event.rawY.toInt()
                if (moveY - downY < 0) { //如果是向上滑动
                    linearLayout!!.translationY = (moveY - downY).toFloat()
                }
            }

            MotionEvent.ACTION_UP ->                 //达到一定比例后，松开手指将关闭弹窗
                if (Math.abs(linearLayout!!.translationY) > linearLayout!!.measuredHeight / 1.5) {
                    Log.e("TAG", "回弹")
                    animDismiss()
                } else {
                    linearLayout!!.translationY = 0f
                }

            else -> {
            }
        }
        return true
    }

}
