<template>
  <div v-loading="loading" element-loading-text="加载中..." class="card-layout">
    <div v-if="cardData.length > 0" class="card-content">
      <div class="card-grid">
        <div
          v-for="item in cardData"
          :key="item.id"
          class="card-grid-item"
          @click="handleCardClick(item)"
          @contextmenu.prevent="(e: MouseEvent) => rightClick(e, item)"
        >
          <CommonCard
            :card-item="item"
            :active="isSelected(item)"
            :show-sku="false"
            :show-product-info="false"
            :image-field="'variantImage'"
            :padding-top="'100%'"
          >
            <template #bottom_left>
              <span
                class="operation-number"
                :title="`操作单号:${item.operationNo}`"
                @click.stop="copyText(item.operationNo ?? '')"
              >
                {{ item.operationNo }}
              </span>
            </template>
            <template #top_left>
              <el-tooltip
                v-if="item.outOfStock"
                effect="light"
                content="缺货"
                placement="bottom"
              >
                <div
                  style="
                    background-color: #f56c6c;
                    color: #fff;
                    padding: 2px 4px;
                    border-radius: 4px;
                    font-size: 12px;
                  "
                >
                  缺
                </div>
              </el-tooltip>
              <span v-if="item.tagsId" class="flex-row flex-row-gap6">
                <el-tag v-for="tag in getItemTags(item.tagsId)" :key="tag.id">
                  {{ tag.name }}
                </el-tag>
              </span>
            </template>
            <template #top_right>
              <img
                v-if="item.craftCode && ['ZPZY', 'CXZY', 'THZY'].includes(item.craftCode as string)"
                :src="`/images/pic/${item.craftCode}.png`"
                width="60"
                height="60"
              />
            </template>
            <template #images>
              <div class="flex-between">
                <div class="images-position">
                  <div v-if="item.imageAry" class="images-container">
                    <div
                      v-for="(img, index) in JSON.parse(item.imageAry as string)"
                      :key="index"
                      :title="img.title"
                      class="item-image"
                    >
                      <el-image
                        :src="img?.url"
                        height="50"
                        :preview-src-list="JSON.parse(item.imageAry as string).map((i: any) => i.url)"
                        :initial-index="index"
                      />
                    </div>
                  </div>
                </div>
                <div class="flex-row flex-row-gap15">
                  <el-tooltip
                    class="item"
                    effect="dark"
                    :content="'用户编码: ' + item?.userMark"
                    placement="bottom"
                  >
                    <span
                      style="
                        white-space: nowrap;
                        overflow: hidden;
                        text-overflow: ellipsis;
                        width: 100%;
                        display: inline-block;
                      "
                      @click.stop="copyText(String(item?.userMark || ''))"
                    >
                      {{ item?.userMark || 'AAAF' }}
                    </span>
                  </el-tooltip>
                  <img
                    v-if="item.platform"
                    :src="`/images/icon/${getPlatformImg(item.platform as string)}`"
                    style="width: 30px; height: 30px"
                  />
                </div>
              </div>
            </template>
            <template #operations>
              <div class="flex-row flex-row-gap6">
                <div
                  v-if="
                    item?.productMark === 'custom_normal' ||
                    item?.productMark === 'normal'
                  "
                  class="product-mark-badge"
                  :title="`类型:${setProductMark(item?.productMark)}类`"
                >
                  {{ setProductMark(item?.productMark) }}
                </div>
                <div
                  v-if="item.customizedQuantity"
                  class="quantity-badge"
                  :class="
                    item.customizedQuantity === 1
                      ? 'single-quantity-badge-color'
                      : 'multiple-quantity-badge-color'
                  "
                  :title="`类型:${
                    item.customizedQuantity === 1 ? '单面' : '双面'
                  }`"
                >
                  {{ item.customizedQuantity === 1 ? '单' : '多' }}
                </div>
                <Icon
                  name="caozuorizhi"
                  style="width: 28px; height: 28px"
                  @click.stop="openLogDialog(item)"
                >
                  <template #title>
                    <title>操作日志</title>
                  </template>
                </Icon>
                <Icon
                  name="chakanxiangqing"
                  @click.stop="handleViewDetail(item)"
                >
                  <template #title>
                    <title>查看详情</title>
                  </template>
                </Icon>
              </div>
            </template>
            <template #info>
              <div class="card-info-grid">
                <div class="card-info-row full">
                  <span
                    class="info-value ellipsis"
                    :title="(item.productName as string) || ''"
                  >
                    {{ item.productName }}
                  </span>
                </div>
                <div class="card-info-row">
                  <span
                    class="info-value clickable ellipsis"
                    :title="`变体SKU:${(item.variantSku as string) || ''}`"
                    @click.stop="copyText((item.variantSku as string) || '')"
                  >
                    {{ item.variantSku }}
                  </span>
                </div>
                <div class="card-info-row">
                  <span class="info-label">工艺：</span>
                  <span class="info-value">{{ item.craftName }}</span>
                </div>
                <div class="card-info-row">
                  <span
                    class="info-value clickable ellipsis"
                    :title="`库存SKU:${(item.thirdSkuCode as string) || ''}`"
                    @click.stop="copyText((item.thirdSkuCode as string) || '')"
                  >
                    {{ item.thirdSkuCode }}
                  </span>
                </div>
                <div class="card-info-row">
                  <span class="info-label">店铺单号：</span>
                  <span
                    class="info-value clickable ellipsis"
                    :title="`店铺单号:${(item.shopNumber as string) || ''}`"
                    @click.stop="copyText((item.shopNumber as string) || '')"
                    >{{ item.shopNumber }}</span
                  >
                </div>
                <div class="card-info-row">
                  <span class="info-label">款号：</span>
                  <span
                    class="info-value clickable ellipsis"
                    :title="`款号:${(item.supplierProductNo as string) || ''}`"
                    @click.stop="
                      copyText((item.supplierProductNo as string) || '')
                    "
                    >{{ item.supplierProductNo }}</span
                  >
                </div>
                <div class="card-info-row">
                  <span class="info-label">客户单号：</span>
                  <span
                    class="info-value clickable ellipsis"
                    :title="`客户单号:${(item.thirdOrderNumber as string) || ''}`"
                    @click.stop="
                      copyText((item.thirdOrderNumber as string) || '')
                    "
                    >{{ item.thirdOrderNumber }}</span
                  >
                </div>
                <div class="card-info-row">
                  <span class="info-label">批次号：</span>
                  <span
                    class="info-value clickable ellipsis"
                    :title="`批次号:${(item.batchArrangeNumber as string) || ''}`"
                    @click.stop="
                      copyText((item.batchArrangeNumber as string) || '')
                    "
                    >{{ item.batchArrangeNumber }}</span
                  >
                </div>
                <div class="card-info-row" style="color: red">
                  <span class="info-label">状态：</span>
                  <span class="info-value">{{ item.statusName }}</span>
                </div>
                <div class="card-info-row full delay-time-row">
                  <span
                    class="delay-time-value"
                    :title="`订单延期:${getOrderDelayText(item.orderCreateTime as string)}`"
                  >
                    {{ getOrderDelayText(item.orderCreateTime as string) }}
                  </span>
                </div>
              </div>
            </template>
          </CommonCard>
        </div>
      </div>
    </div>
    <div v-else class="card-empty">暂无数据</div>

    <div class="card-pagination">
      <div class="card-selected-info">
        已选择
        <span class="highlight">{{ selectedItems.length }}</span>
        条数据
      </div>
      <ElPagination
        :current-page="currentPage"
        :page-size="pageSize"
        :page-sizes="[50, 100, 200, 300, 500]"
        background
        layout="total, sizes, prev, pager, next, jumper"
        :total="total"
        style="margin: 0 auto"
        @size-change="onPageSizeChange"
        @current-change="onCurrentPageChange"
      />
    </div>
    <el-dialog
      v-model="logVisible"
      title="操作日志"
      width="1000px"
      :close-on-click-modal="false"
    >
      <LogList :log-list="logList" />
      <div v-if="!logList.length" class="empty-content">暂无数据</div>
    </el-dialog>
  </div>
  <RightClickMenu
    ref="rightMenuRef"
    :show-copy-count="false"
    :show-copy-sub-shop-number="false"
    @on-change="rightChange"
  >
    <template #default>
      <div class="menu-item" @click="rightChange('order-number')">
        复制订单号
      </div>
      <div class="menu-item" @click="rightChange('operationNo')">
        复制操作单号
      </div>
    </template>
  </RightClickMenu>
</template>

<script setup lang="ts">
import { ref } from 'vue'
import dayjs from 'dayjs'
import { ElMessage } from 'element-plus'
import {
  getCardLayoutListApi,
  getFactoryOrderNewLogApi,
} from '@/api/factoryOrderNew'
import type { PaginationData } from '@/types/api'
import type { CardLayoutListFetcher } from '@/types/api/factoryOrderNew'
import usePageList from '@/utils/hooks/usePageList'
import { operateOrderListData } from '@/types/api/factoryOrderNew'
import type { LogListData } from '@/types/api/order'
import LogList from '@/components/LogList.vue'
import RightClickMenu from '@/components/RightClickMenu.vue'
import platformJson from '../../../../json/platform.json'

const props = defineProps<{
  status?: string
  queryPayload?: Record<string, unknown>
  initPageSize?: number
  tagList?: { id: string; name: string }[]
  fetchList?: CardLayoutListFetcher
}>()

const buildListPayload = () => {
  const payload = { ...props.queryPayload }
  if (props.fetchList || props.status === undefined) {
    return payload
  }
  return {
    ...payload,
    status: props.status === 'ALL' ? undefined : props.status,
  }
}

const emit = defineEmits<{
  'selection-change': [items: operateOrderListData[]]
  'view-detail': [item: operateOrderListData]
}>()

const {
  loading,
  currentPage,
  pageSize,
  total,
  data: cardData,
  onCurrentPageChange,
  onPageSizeChange,
  refresh,
} = usePageList<operateOrderListData>({
  initPageSize: props.initPageSize || 100,
  initLoad: false,
  query: async (current, size) => {
    const payload = buildListPayload()
    if (props.fetchList) {
      return props.fetchList(payload, current, size)
    }
    const res = await getCardLayoutListApi(payload, current, size)
    return res.data as unknown as PaginationData<operateOrderListData>
  },
})

const selectedItems = ref<operateOrderListData[]>([])
const logVisible = ref(false)
const logList = ref<LogListData[]>([])
const rightMenuRef = ref()
const rightClickItem = ref<operateOrderListData | null>(null)

const isSelected = (item: operateOrderListData) =>
  selectedItems.value.some((s) => s.id === item.id)

const getItemTags = (tagsId?: string) => {
  if (!tagsId || !props.tagList?.length) return []
  return tagsId
    .split(',')
    .map((id) => id.trim())
    .filter(Boolean)
    .map((id) => props.tagList!.find((tag) => String(tag.id) === id))
    .filter((tag): tag is { id: string; name: string } => !!tag)
}

const handleCardClick = (item: operateOrderListData) => {
  const idx = selectedItems.value.findIndex((s) => s.id === item.id)
  if (idx >= 0) {
    selectedItems.value.splice(idx, 1)
  } else {
    selectedItems.value.push(item)
  }
  emit('selection-change', [...selectedItems.value])
}

const handleViewDetail = (item: operateOrderListData) => {
  emit('view-detail', item)
}

const copyText = (text: string) => {
  navigator.clipboard.writeText(text)
  ElMessage.success('复制成功')
}

const rightClick = (e: MouseEvent, item: operateOrderListData) => {
  rightClickItem.value = item
  rightMenuRef.value?.setPosition({
    x: e.clientX,
    y: e.clientY,
  })
}

const getRightCopyData = () => {
  if (selectedItems.value.length > 0) return selectedItems.value
  if (rightClickItem.value) return [rightClickItem.value]
  return []
}

const rightChange = (code: string) => {
  if (code === 'select-all') {
    selectedItems.value = [...(cardData.value as operateOrderListData[])]
    emit('selection-change', [...selectedItems.value])
  } else if (code === 'cancel-select') {
    selectedItems.value = []
    emit('selection-change', [])
  } else if (code === 'copy_shopNumber') {
    const str = getRightCopyData()
      .map((item) => item?.shopNumber)
      .filter(Boolean)
      .join(',')
    if (!str) return ElMessage.warning('当前数据没有店铺单号')
    navigator.clipboard.writeText(str)
    ElMessage.success('复制成功')
  } else if (code === 'order-number') {
    const str = getRightCopyData()
      .map((item) => item?.podOrderNo)
      .filter(Boolean)
      .join(',')
    if (!str) return ElMessage.warning('当前数据没有订单号')
    navigator.clipboard.writeText(str)
    ElMessage.success('复制成功')
  } else if (code === 'operationNo') {
    const str = getRightCopyData()
      .map((item) => item?.operationNo)
      .filter(Boolean)
      .join(',')
    if (!str) return ElMessage.warning('当前数据没有操作单号')
    navigator.clipboard.writeText(str)
    ElMessage.success('复制成功')
  }
}

const openLogDialog = async (item: operateOrderListData) => {
  if (!item.podOrderId) return
  const loading = ElLoading.service({
    fullscreen: true,
    text: '加载中...',
    background: 'rgba(0, 0, 0, 0.3)',
  })
  try {
    const res = await getFactoryOrderNewLogApi(item.podOrderId as number)
    logList.value = (res.data || []) as unknown as LogListData[]
    logVisible.value = true
  } catch (e) {
    // ignore
  } finally {
    loading.close()
  }
}

const clearSelection = () => {
  selectedItems.value = []
  emit('selection-change', [])
}
function setProductMark(productMark: string) {
  if (!productMark) return ''
  if (productMark === 'custom_normal') return 'CB'
  if (productMark === 'normal') return 'G'
  return ''
}

const getSelectedIds = () => selectedItems.value.map((i) => i.id)
const getPlatformImg = (code: string) => {
  const lowerCode = code.toLowerCase()
  const item = platformJson.find((el) =>
    el.type.toLowerCase().includes(lowerCode),
  )
  if (item) {
    return item.icon.split('/').pop()
  }
  return ''
}

const getOrderDelayText = (createTime?: string | null) => {
  if (!createTime) return '--'
  const createAt = dayjs(createTime)
  if (!createAt.isValid()) return '--'
  const diffMinutes = Math.max(0, dayjs().diff(createAt, 'minute'))
  const baseHours = Math.floor(diffMinutes / 60)
  const remainMinutes = diffMinutes % 60
  const hours = baseHours + (remainMinutes > 30 ? 1 : 0)
  return `${hours}h`
}

defineExpose({ clearSelection, getSelectedIds, refresh })
</script>

<style scoped lang="scss">
.card-layout {
  display: flex;
  flex-direction: column;
  height: 100%;
  overflow: hidden;
}
.card-content {
  flex: 1;
  overflow-y: auto;
}

.card-grid {
  display: grid;
  grid-template-columns: repeat(5, minmax(0, 1fr));
  grid-template-rows: max-content;
  gap: 10px;
  padding: 5px;
}

.card-grid-item {
  cursor: pointer;
}

.card-empty {
  flex: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  color: #909399;
  font-size: 14px;
}

.card-pagination {
  flex-shrink: 0;
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 10px 0;
}

.card-selected-info {
  font-size: 14px;
  color: #606266;

  .highlight {
    color: red;
    font-weight: bold;
  }
}

.operation-number {
  font-size: 12px;
  cursor: pointer;
  background: rgba(255, 255, 255, 0.75);
  padding: 2px 6px;
  border-radius: 4px;
  max-width: 100%;
  display: inline-block;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.quantity-badge {
  background-color: #f56c6c;
  color: #fff;
  padding: 5px 8px;
  border-radius: 4px;
  font-size: 12px;
}

.multiple-quantity-badge-color {
  background-color: #e6a23c;
}

.product-mark-badge {
  border: 2px solid #f56c6c;
  color: #f56c6c;
  font-weight: 700;
  height: 28px;
  width: 28px;
  text-align: center;
  border-radius: 6px;
  font-size: 16px;
}

.card-info-grid {
  display: grid;
  grid-template-columns: 1fr 150px;
  gap: 4px;
  font-size: 12px;
  margin-top: 6px;

  .full {
    grid-column: 1 / -1;
  }
}

.card-info-row {
  display: flex;
  overflow: hidden;
}

.delay-time-row {
  justify-content: flex-end;
  margin-top: 2px;
}

.delay-time-value {
  color: red;
  font-weight: 600;
}

.info-label {
  flex-shrink: 0;
  color: #909399;
}

.info-value {
  flex: 1;
  min-width: 0;

  &.ellipsis {
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }

  &.clickable {
    cursor: pointer;
    color: #409eff;

    &:hover {
      text-decoration: underline;
    }
  }
}
.flex-between {
  display: flex;
  justify-content: space-between;
  align-items: center;
  width: 100%;
  overflow: hidden;
  gap: 6px;

  .images-position {
    flex: 1;
    overflow: auto hidden;
    .images-container {
      width: 100%;
      display: flex;
      gap: 6px;
    }
    .item-image {
      width: 50px;
      min-width: 50px;
      height: 50px;
      border: 1px solid #eee;
      cursor: pointer;

      img {
        width: 100%;
        height: 100%;
        object-fit: cover;
      }
    }
  }

  b {
    margin-right: 5px;
    font-size: 15px;
  }
}

.flex-row {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 15px;
}
.flex-row-gap15 {
  gap: 15px;
}
.flex-row-gap6 {
  gap: 6px;
}
@media (max-width: 1920px) {
  .card-grid {
    grid-template-columns: repeat(5, minmax(0, 1fr));
  }
}
@media (max-width: 1750px) {
  .card-grid {
    grid-template-columns: repeat(4, minmax(0, 1fr));
  }
  .card-info-grid {
    grid-template-columns: 1fr 180px;
  }
}
@media (max-width: 1550px) {
  .card-grid {
    grid-template-columns: repeat(3, minmax(0, 1fr));
  }
  .card-info-grid {
    grid-template-columns: 1fr 200px;
  }
}
</style>
