import { ref, onMounted, onUnmounted } from 'vue'

/**
 * 表格自适应容器剩余高度。
 * - 用 getBoundingClientRect + innerHeight 计算可用高度（不依赖 CSS 高度级联）
 * - 组件挂载后持续重试 5 秒，覆盖异步数据加载后分页出现的情况
 */
export function useTableHeight() {
  const tableHeight = ref(200)
  const containerRef = ref(null)
  let observer = null
  let timer = null

  const getMarginHeight = (el) => {
    if (!el) return 0
    const oh = el.offsetHeight
    if (oh === 0) {
      // v-show 隐藏的元素，offsetHeight=0，无法取到高度
      // 返回 0 由调用方决定是否需要预留空间
      return 0
    }
    const style = window.getComputedStyle(el)
    return oh
      + (parseFloat(style.marginTop) || 0)
      + (parseFloat(style.marginBottom) || 0)
  }

  const calcHeight = () => {
    if (!containerRef.value) return false
    const container = containerRef.value
    const rect = container.getBoundingClientRect()
    // 可用高度 = 视口高度 - 容器到视口顶部的距离
    const ch = window.innerHeight - rect.top
    if (ch <= 0) return false

    let used = 0
    const cs = window.getComputedStyle(container)
    used += parseFloat(cs.paddingTop) || 0
    used += parseFloat(cs.paddingBottom) || 0

    let hasHiddenPagination = false

    for (const child of container.children) {
      if (child.classList?.contains('table-wrapper')) continue
      if (child.classList?.contains('el-dialog')) continue
      const h = getMarginHeight(child)
      used += h
      // 检测是否有隐藏的分页组件（v-show="total > 0" 时 total 初始为 0）
      if (h === 0 && child.classList?.contains('pagination-container')) {
        hasHiddenPagination = true
      }
    }

    // 如果检测到隐藏的分页，预留约 50px 空间（分页高度 + margin-top）
    // 这样即使分页稍后出现，也不会把内容挤出 overflow:hidden
    if (hasHiddenPagination) {
      used += 50
    }

    const h = ch - used
    if (h > 200) {
      tableHeight.value = h
      return true
    }
    return false
  }

  onMounted(() => {
    // 立即计算一次
    requestAnimationFrame(() => calcHeight())

    // 持续重试 5 秒，覆盖异步数据加载后分页出现的情况
    let retry = 0
    if (timer) clearInterval(timer)
    timer = setInterval(() => {
      calcHeight()
      if (++retry >= 25) {
        clearInterval(timer)
        timer = null
      }
    }, 200)

    window.addEventListener('resize', calcHeight)
    if (containerRef.value && window.ResizeObserver) {
      observer = new ResizeObserver(calcHeight)
      observer.observe(containerRef.value)
    }
  })

  onUnmounted(() => {
    window.removeEventListener('resize', calcHeight)
    if (timer) { clearInterval(timer); timer = null }
    if (observer) { observer.disconnect(); observer = null }
  })

  return { tableHeight, containerRef, updateHeight: calcHeight }
}
