package com.adealink.weparty.commonui.recycleview.itemdecoration


import android.content.Context
import android.graphics.Canvas
import android.graphics.Rect
import android.graphics.drawable.Drawable
import android.graphics.drawable.GradientDrawable
import android.util.Log
import android.view.View
import android.widget.LinearLayout
import androidx.recyclerview.widget.RecyclerView
import com.adealink.weparty.commonui.drawabletoolbox.DrawableBuilder

/**
 * 基于DividerItemDecoration进行扩展
 */
class CustomDividerItemDecoration(
    context: Context
) : RecyclerView.ItemDecoration() {

    /**
     * 自定义分割线颜色+高度
     */
    fun setDivider(dividerHeight: Int, dividerColor: Int) {
        val dividerDrawable = DrawableBuilder()
            .shape(GradientDrawable.RECTANGLE)
            .solidColor(dividerColor)
            .height(dividerHeight)
            .build()
        setDrawable(dividerDrawable)
    }

    /**
     * 自定义分割线展示条件
     */
    private var needSpacePredicate: (Int) -> Boolean = { true } // 新增支持的判断函数
    fun setNeedSpacePredicate(predicate: (Int) -> Boolean) {
        needSpacePredicate = predicate
    }

    companion object {
        const val HORIZONTAL = LinearLayout.HORIZONTAL
        const val VERTICAL = LinearLayout.VERTICAL
        private const val TAG = "DividerItem"
        private val ATTRS = intArrayOf(android.R.attr.listDivider)
    }

    private var mDivider: Drawable? = null
    private var mOrientation: Int = VERTICAL
    private val mBounds = Rect()

    init {
        val a = context.obtainStyledAttributes(ATTRS)
        mDivider = a.getDrawable(0)
        if (mDivider == null) {
            Log.w(
                TAG, "@android:attr/listDivider was not set in the theme used for this " +
                        "DividerItemDecoration. Please set that attribute or call setDrawable()"
            )
        }
        a.recycle()
    }

    fun setOrientation(orientation: Int) {
        require(orientation == HORIZONTAL || orientation == VERTICAL) {
            "Invalid orientation. It should be either HORIZONTAL or VERTICAL"
        }
        mOrientation = orientation
    }

    fun setDrawable(drawable: Drawable) {
        requireNotNull(drawable) { "Drawable cannot be null." }
        mDivider = drawable
    }

    fun getDrawable(): Drawable? {
        return mDivider
    }

    override fun onDraw(c: Canvas, parent: RecyclerView, state: RecyclerView.State) {
        if (parent.layoutManager == null || mDivider == null) return

        if (mOrientation == VERTICAL) {
            drawVertical(c, parent)
        } else {
            drawHorizontal(c, parent)
        }
    }

    private fun drawVertical(canvas: Canvas, parent: RecyclerView) {
        canvas.save()
        val left: Int
        val right: Int

        if (parent.clipToPadding) {
            left = parent.paddingLeft
            right = parent.width - parent.paddingRight
            canvas.clipRect(left, parent.paddingTop, right, parent.height - parent.paddingBottom)
        } else {
            left = 0
            right = parent.width
        }

        val totalCount = parent.adapter!!.itemCount
        val childCount = parent.childCount
        for (i in 0 until childCount) {
            val child = parent.getChildAt(i)
            val position = parent.getChildAdapterPosition(child)
            if (position == RecyclerView.NO_POSITION) continue
            if (position >= totalCount - 1) continue


            // 使用 needSpacePredicate 判断是否需要绘制分割线
            if (!needSpacePredicate(position)) continue

            parent.getDecoratedBoundsWithMargins(child, mBounds)
            val bottom = mBounds.bottom + Math.round(child.translationY)
            val top = bottom - mDivider!!.intrinsicHeight
            mDivider!!.setBounds(left, top, right, bottom)
            mDivider!!.draw(canvas)
        }
        canvas.restore()
    }

    private fun drawHorizontal(canvas: Canvas, parent: RecyclerView) {
        canvas.save()
        val top: Int
        val bottom: Int

        if (parent.clipToPadding) {
            top = parent.paddingTop
            bottom = parent.height - parent.paddingBottom
            canvas.clipRect(parent.paddingLeft, top, parent.width - parent.paddingRight, bottom)
        } else {
            top = 0
            bottom = parent.height
        }

        val childCount = parent.childCount
        for (i in 0 until childCount) {
            val child = parent.getChildAt(i)
            val position = parent.getChildAdapterPosition(child)
            // 使用 needSpacePredicate 判断是否需要绘制分割线
            if (!needSpacePredicate(position)) continue

            parent.layoutManager!!.getDecoratedBoundsWithMargins(child, mBounds)
            val right = mBounds.right + Math.round(child.translationX)
            val left = right - mDivider!!.intrinsicWidth
            mDivider!!.setBounds(left, top, right, bottom)
            mDivider!!.draw(canvas)
        }
        canvas.restore()
    }

    override fun getItemOffsets(
        outRect: Rect,
        view: View,
        parent: RecyclerView,
        state: RecyclerView.State
    ) {
        if (mDivider == null) {
            outRect.set(0, 0, 0, 0)
            return
        }

        val position = parent.getChildAdapterPosition(view)
        // 使用 needSpacePredicate 判断是否需要绘制分割线
        if (!needSpacePredicate(position)) {
            outRect.set(0, 0, 0, 0)
            return
        }

        if (mOrientation == VERTICAL) {
            outRect.set(0, 0, 0, mDivider!!.intrinsicHeight)
        } else {
            outRect.set(0, 0, mDivider!!.intrinsicWidth, 0)
        }
    }
}