<template>
  <XtfConfigProvider class="demo-theme-root" :theme="demoTheme">
  <scroll-view class="xtf-demo-scroll xtf-page-scroll" direction="vertical">
    <view class="xtf-demo-page xtf-page-scroll-content">
      <text class="xtf-demo-title">Virtual List</text>
      <view class="xtf-demo-stats">
        <text class="xtf-demo-value demo-total">总数 {{ items.length }}</text>
        <text class="xtf-demo-value demo-range">渲染范围 [{{ rangeStart }}, {{ rangeEnd }})</text>
        <text class="xtf-demo-value demo-rendered">渲染 {{ rangeEnd - rangeStart }} 条</text>
        <text class="xtf-demo-value demo-visible">可见索引 {{ visibleStart }} - {{ visibleEnd }}</text>
      </view>
      <view class="xtf-demo-control">
        <text class="xtf-demo-label">缓冲区 {{ bufferSize }} 条</text>
        <slider class="demo-buffer" :value="bufferSize" :min="0" :max="12" :step="1" activeColor="#2563eb" @change="changeBuffer" />
      </view>
      <view class="xtf-demo-actions">
        <input class="xtf-demo-input demo-index" type="number" v-model="targetIndex" placeholder="索引 0 起" />
        <button class="xtf-demo-button demo-jump" size="mini" @click="jumpToIndex">跳转</button>
        <button class="xtf-demo-button demo-top" size="mini" @click="backToTop">回顶部</button>
      </view>
      <view class="xtf-demo-actions">
        <button class="xtf-demo-button demo-bottom" size="mini" @click="jumpToBottom">到末尾</button>
        <button class="xtf-demo-button demo-reset" size="mini" @click="reset">重置</button>
        <button class="xtf-demo-button demo-ten-thousand" size="mini" @click="useTenThousand">切换一万条</button>
        <text class="xtf-demo-status demo-load-state">{{ loadingMore ? '加载中' : (finished ? '已全部加载' : '待加载') }}</text>
      </view>
      <view class="xtf-demo-list">
        <XtfVirtualList ref="virtualList" :items="items" :item-height="rowHeight" :visible-count="6" :buffer-size="bufferSize" :loading-more="loadingMore" :finished="finished" @scroll="onScroll" @visible-range-change="onRangeChange" @scroll-to-lower="loadMore">
          <template #default="slotProps">
            <view class="xtf-demo-row" :class="{ 'xtf-demo-row-even': slotProps.index % 2 === 1 }">
              <text class="xtf-demo-number">{{ slotProps.index }}</text>
              <view class="xtf-demo-row-main">
                <text class="xtf-demo-row-title">{{ slotProps.item.name }}</text>
                <text class="xtf-demo-row-detail">{{ slotProps.item.code }}</text>
              </view>
              <text class="xtf-demo-row-status" :class="{ 'xtf-demo-row-pending': slotProps.item.pending }">{{ slotProps.item.pending ? '待处理' : '已完成' }}</text>
            </view>
          </template>
        </XtfVirtualList>
      </view>
      <text class="xtf-demo-message demo-message">{{ message }}</text>
    </view>
  </scroll-view>
  </XtfConfigProvider>
</template>
<script setup lang="uts">
import { useDemoTheme } from '@/pages/demo-theme.uts'
import XtfConfigProvider from '@/uni_modules/xtf-linkuiunix/components/xtf-config-provider/xtf-config-provider.uvue'
const demoTheme = useDemoTheme()
import { computed, nextTick, onUnmounted, ref } from "vue"
import XtfVirtualList from "@/uni_modules/xtf-linkuiunix/components/xtf-virtual-list/xtf-virtual-list.uvue"
const rowHeight = 60
const virtualList = ref<any>(null)
function createItems(start: number, count: number): any[] {
  return Array.from({ length: count }, (_item: any, index: number): any => ({ id: start + index, name: "订单 " + (start + index + 1).toString(), code: "VL-" + (100000 + start + index).toString(), pending: (start + index) % 3 === 0 }))
}
const items = ref<any[]>(createItems(0, 1000))
const bufferSize = ref(4)
const targetIndex = ref("500")
const rangeStart = ref(0)
const rangeEnd = ref(0)
const currentTop = ref(0)
const loadingMore = ref(false)
const finished = ref(false)
const message = ref("初始 1000 条")
let loadTimer = 0
const visibleStart = computed((): number => Math.min(items.value.length - 1, Math.floor(currentTop.value / rowHeight)))
const visibleEnd = computed((): number => Math.min(items.value.length - 1, Math.ceil((currentTop.value + 360) / rowHeight) - 1))
function changeBuffer(event: UniSliderChangeEvent): void { bufferSize.value = event.detail.value }
function onScroll(payload: any): void { currentTop.value = payload.scrollTop }
function onRangeChange(payload: any): void { rangeStart.value = payload.startIndex; rangeEnd.value = payload.endIndex }
function jumpToIndex(): void {
  const value = Number(targetIndex.value)
  if (targetIndex.value.trim().length === 0 || !Number.isFinite(value)) { message.value = "请输入有效索引"; return }
  const index = Math.max(0, Math.min(items.value.length - 1, Math.floor(value)))
  targetIndex.value = index.toString()
  virtualList.value?.scrollToIndex(index)
  message.value = "跳转索引 " + index.toString()
}
function backToTop(): void { virtualList.value?.scrollToIndex(0); message.value = "已回顶部" }
function jumpToBottom(): void { virtualList.value?.scrollToIndex(items.value.length - 1) }
function loadMore(): void {
  if (loadingMore.value || finished.value) return
  loadingMore.value = true
  message.value = "正在追加 100 条"
  loadTimer = setTimeout(() => {
    loadTimer = 0
    items.value = items.value.concat(createItems(items.value.length, 100))
    finished.value = items.value.length >= 1300
    loadingMore.value = false
    message.value = finished.value ? "全部 1300 条已加载" : "已追加 100 条"
  }, 800)
}
function reset(): void {
  if (loadTimer !== 0) { clearTimeout(loadTimer); loadTimer = 0 }
  loadingMore.value = false
  finished.value = false
  items.value = createItems(0, 1000)
  bufferSize.value = 4
  targetIndex.value = "500"
  currentTop.value = 0
  message.value = "已重置为 1000 条"
  nextTick(() => { virtualList.value?.scrollToIndex(0) })
}
function useTenThousand(): void {
  if (loadTimer !== 0) { clearTimeout(loadTimer); loadTimer = 0 }
  loadingMore.value = false
  finished.value = true
  items.value = createItems(0, 10000)
  currentTop.value = 0
  targetIndex.value = "9999"
  message.value = "已切换为 10000 条，可跳转末尾或滚动查看渲染范围"
  nextTick(() => { virtualList.value?.scrollToIndex(0) })
}
onUnmounted(() => { if (loadTimer !== 0) clearTimeout(loadTimer) })
</script>
<style>
.xtf-demo-scroll { display: flex; flex-direction: column; flex: 1; width: 100%; height: 100%; }
.xtf-demo-page { display: flex; flex-direction: column; width: 100%; padding: 24rpx; background-color: var(--xtf-color-page, #f8fafc); }
.xtf-demo-title { color: var(--xtf-color-text, #0f172a); font-size: 36rpx; font-weight: 700; }
.xtf-demo-stats { display: flex; flex-direction: row; flex-wrap: wrap; margin-top: 16rpx; }
.xtf-demo-value { margin-right: 24rpx; margin-bottom: 8rpx; color: var(--xtf-color-text-secondary, #475569); font-size: 24rpx; }
.xtf-demo-control { display: flex; flex-direction: column; margin-top: 12rpx; }
.xtf-demo-label { color: var(--xtf-color-text-secondary, #334155); font-size: 24rpx; }
.xtf-demo-actions { display: flex; flex-direction: row; flex-wrap: wrap; align-items: center; margin-top: 12rpx; }
.xtf-demo-input { flex: 1; min-width: 100rpx; height: 36px; margin-right: 12rpx; padding: 0 16rpx; border-width: 1px; border-style: solid; border-color: var(--xtf-color-border, #cbd5e1); border-radius: 4px; background-color: var(--xtf-color-surface, #ffffff); font-size: 26rpx; color: var(--xtf-color-text, #0f172a); }
.xtf-demo-button { margin: 0 12rpx 8rpx 0; }
.xtf-demo-status { color: var(--xtf-color-text-secondary, #64748b); font-size: 24rpx; }
.xtf-demo-list { display: flex; flex-direction: column; flex-shrink: 0; height: 360px; margin-top: 16rpx; }
.xtf-demo-row { display: flex; flex-direction: row; align-items: center; width: 100%; height: 100%; padding: 0 16rpx; background-color: var(--xtf-color-surface, #ffffff); }
.xtf-demo-row-even { background-color: var(--xtf-color-surface-muted, #f1f5f9); }
.xtf-demo-number { width: 64rpx; flex-shrink: 0; color: var(--xtf-color-text-secondary, #64748b); font-size: 22rpx; }
.xtf-demo-row-main { display: flex; flex-direction: column; flex: 1; min-width: 0; }
.xtf-demo-row-title { color: var(--xtf-color-text, #1e293b); font-size: 26rpx; }
.xtf-demo-row-detail { margin-top: 4rpx; color: var(--xtf-color-text-secondary, #64748b); font-size: 22rpx; }
.xtf-demo-row-status { margin-left: 12rpx; color: #15803d; font-size: 22rpx; }
.xtf-demo-row-pending { color: #b45309; }
.xtf-demo-message { margin-top: 16rpx; color: var(--xtf-color-text-secondary, #475569); font-size: 24rpx; }
</style>
