/** @jsxImportSource vue */
import { defineComponent, ref, computed, watch, defineEmits, onUnmounted } from 'vue'
import {
  ElCard,
  ElDrawer,
  ElTag,
  ElDescriptions,
  ElDescriptionsItem,
  ElButton,
  ElIcon,
  ElCheckbox,
  ElCheckboxGroup,
  ElBreadcrumb,
  ElLink,
  ElEmpty,
  ElDivider
} from 'element-plus'
import NormalColumnContent from '../normal-column-content.vue'
import CardView from '../../../../src/components/Card'
import CompactCard from './CompactCard/index.vue'
import Scrollbar from '../../../../src/components/Scrollbar'
import store from '../store'
import { apisMixin } from '../apis'
import eventBus from '../eventBus'
import { useI18n } from 'vue-i18n'
import { getClobalComponentSuperGridSetting } from '../../../../src/utils/global-component-setting.ts'

import { ArrowLeft, Bottom, CirclePlus, Loading, Tickets } from '@element-plus/icons-vue'
// import { $emit, $off, $on } from '@/utils/gogocodeTransfer'

export default defineComponent({
  name: 'MobileTableCard',
  components: {
    NormalColumnContent,
    CardView,
    CompactCard,
    Scrollbar
  },
  mixins: [apisMixin],
  props: {
    // 展示字段限制
    showFieldCount: {
      type: [Number, undefined],
      default: () => 5
    },
    // 列字段数据
    columns: {
      type: Array,
      default: () => []
    },
    // 表格数据
    data: {
      type: Array,
      default: () => []
    },
    // 字段事件 v-bind 与 v-on 集成
    getColumnComponentData: {
      type: [Function, undefined],
      default: undefined
    },
    // 选中页
    currentPage: {
      type: [Number],
      default: 1
    },
    // 一页展示数量
    pageSize: {
      type: [Number],
      default: 20
    },
    // 一页展示数量
    pageTotal: {
      type: [Number],
      default: 0
    },
    // 是否开启 堆积分页数据
    isStackingPaginatedData: {
      type: Boolean,
      default: () => false
    },
    listCode: {
      type: String,
      default: null
    },
    // 是否启用行编辑
    isEnableEdit: {
      type: Boolean,
      default: () => false
    },
    isSubTable: {
      type: Boolean,
      default: () => false
    }
  },
  setup(props, setupData) {
    const $emits = defineEmits([
      'currentChange',
      'update:current-page',
      'select',
      'selectionChange',
      'rowDblclick',
      'rowClick',
      'scrollToBottom'
    ])
    const { t } = useI18n()
    const { attrs, emit, expose } = setupData

    console.log(
      '*mobile-table-card.JSX**********************************************=>',
      props,
      attrs,
      setupData,
      expose
    )

    // 分页加载状态
    const isPaginationLoading = ref(false)

    const paginationList = ref([])
    // 选中数据
    const checkedList = ref([])
    // 当前勾选ID
    const checkedClickId = ref(undefined)
    // 当前选中数据
    const isCheckedIndex = ref(undefined)

    // 是否打开子表弹窗
    const isChildrenDrawer = ref(false)

    // 子表打开历史数据
    const childrenBreadcrumbData = ref([])

    // 是否有子记录
    const isDataChildren = ref(false)

    // 是否自定义 开启 Add
    const customizeAddColumnBtn = ref(undefined)

    const gridParams = store.get(props.listCode)

    // 是否默认开启行编辑
    const allRowDefaultEditable = gridParams?.options?.allEditable ?? false

    // DEFAULT、COMPACT
    let mobileSuperGridShowType = 'DEFAULT'
    let mobileSuperGridLabelWidth = 'ALIGN_LABEL_WIDTH'
    const componentSettingJSON = getClobalComponentSuperGridSetting()
    if (componentSettingJSON) {
      try {
        const componentSetting = JSON.parse(componentSettingJSON)
        const settingMobileType = componentSetting.mobileSuperGridShowType
        if (settingMobileType) {
          mobileSuperGridShowType = settingMobileType
        }
        const settingLabelWidth = componentSetting.mobileSuperGridLabelWidth
        if (settingLabelWidth) {
          mobileSuperGridLabelWidth = settingLabelWidth
        }
      } catch (error) {
        console.error('解析全局组件设置失败', error)
      }
    }
    const isCompact = mobileSuperGridShowType === 'COMPACT'

    const setPaginationList = (data) => {
      if (props.isStackingPaginatedData) {
        paginationList.value[(props.currentPage ?? 1) - 1] = data
      } else {
        paginationList.value[0] = data
      }
      isPaginationLoading.value = false
    }

    setPaginationList(props.data)

    const addColumnBtn = computed(() => {
      const gridParams = store.get(props.listCode)
      const showOperationButton = gridParams?.options?.showOperationButton ?? false
      const isFormSubTable = gridParams?.options?.isFormSubTable ?? false
      const subTableCanAdd = gridParams?.options?.subTableCanAdd ?? false
      const isOperation = componentDatas.value?.some(({ prop }) => ['operation'].includes(prop))
      return customizeAddColumnBtn.value ?? (showOperationButton && isFormSubTable && subTableCanAdd && isOperation)
    })

    eventBus.$on('change-add-state', (is) => (customizeAddColumnBtn.value = is))
    // 列表数据
    const dataList = computed(() => {
      if (props.isStackingPaginatedData) {
        return paginationList.value.flatMap((data, index) => (index + 1 <= props.currentPage ? data : []))
      } else {
        return paginationList.value[0] ?? []
      }
    })

    // 获取包含所有子表数据 LIST 一般用于勾选
    const dataChildrenList = computed(() => {
      const getChildrenData = (data) => {
        return (
          data?.flatMap((item) => {
            if (item?.children?.length) return [item, ...getChildrenData(item.children)]
            return [item]
          }) ?? []
        )
      }
      return getChildrenData(dataList.value)
    })

    const isLoadPaginationData = computed(() => {
      if (props.isStackingPaginatedData) {
        return (paginationList.value[props.currentPage - 1]?.length ?? 0) > 0
      } else {
        return dataList.value.length < props.pageSize * props.currentPage && pagesNumber.value >= props.currentPage
      }
    })

    // 面包屑数据
    const childrenList = computed(() => {
      return childrenBreadcrumbData.value[childrenBreadcrumbData.value.length - 1]?.children ?? []
    })

    const componentDatas = computed(() => {
      const getChildrenData = (data) => {
        return (
          data?.flatMap((item) => {
            if (item?.children?.length) return getChildrenData(item.children)
            return [item]
          }) ?? []
        )
      }
      return getChildrenData(
        props.columns.filter((column) => (!column ? false : !['$selection', '$index'].includes(column?.prop)))
      )
    })

    const layoutData = computed(() => {
      const contentData = componentDatas.value.map((data, index) => {
        if (data.operations) {
          data.layoutModelType = 'footer'
        } else {
          data.layoutModelType = 'content'
        }
        return data
      })
      const content = contentData.filter(({ layoutModelType }) => ['content'].includes(layoutModelType))
      return {
        header: content[0] ? [content[0]] : [],
        content,
        footer: contentData.filter(({ layoutModelType }) => ['footer'].includes(layoutModelType))
      }
    })

    // 获取最大 label 字符长度
    const getLongestStringLength = (strArray) => {
      return strArray.reduce((maxLen, str) => {
        return Math.max(
          maxLen,
          [...str].reduce((len, char) => (/[\u4e00-\u9fff]/.test(char) ? len + 2 : len + 1), 0)
        )
      }, 0)
    }

    // 分页数量
    const pagesNumber = computed(() => {
      if (!props.pageTotal) return 0
      console.log('计算分页数量', Math.ceil(props.pageTotal / props.pageSize))
      return Math.ceil(props.pageTotal / props.pageSize)
    })

    // 字段更多 是否开启
    const isShowDetailsMore = computed(() => {
      if (props.showFieldCount && layoutData.value.content.length > props.showFieldCount) return true
      return false
    })

    // 是否显示卡片底部控件
    const isShowFooter = computed(() => {
      return layoutData.value.footer.length > 0
    })

    const maxLabelWidth = computed(() => {
      return getLongestStringLength(layoutData.value.content.map((column) => column?.label ?? 0)) * 7 + 15
    })

    const isCheck = computed(() => {
      return props.columns.some((column) => ['$selection'].includes(column?.prop))
    })

    const isIndex = computed(() => {
      return props.columns.some((column) => ['$index'].includes(column?.prop))
    })

    const isAllChecked = computed(() => {
      if (dataChildrenList.value.length === 0) return false
      return dataChildrenList.value.every(({ $rowDataGuId }) => checkedList.value.includes($rowDataGuId))
    })

    const isIndeterminate = computed(() => {
      if (checkedList.value.length === 0) return false
      return (
        !isAllChecked.value &&
        dataChildrenList.value.some(({ $rowDataGuId }) => checkedList.value.includes($rowDataGuId))
      )
    })

    const detailsFormData = computed(() => {
      return dataList.value[isCheckedIndex.value]
    })

    // 写入选中
    const setCheckedList = (value) => {
      if (!isCheck.value) return
      if (checkedList.value.includes(value)) {
        checkedList.value = checkedList.value.filter((v) => v !== value)
      } else {
        checkedList.value = [...new Set([...checkedList.value, value])]
      }
      checkedClickId.value = value
    }

    const toggleSelectAll = () => {
      if (isAllChecked.value) {
        checkedList.value = []
      } else {
        checkedList.value = dataChildrenList.value.map(({ $rowDataGuId }) => $rowDataGuId)
      }
    }

    const clearSelection = () => {
      checkedList.value = []
    }

    const isValidateError = (columnFormData, columnIndex, column) => {
      const isFormSubTable = gridParams?.options?.isFormSubTable ?? false
      return (
        isFormSubTable &&
        columnFormData &&
        columnFormData['validateErrorField'] &&
        columnFormData['validateErrorField'] === column.prop
      )
    }

    /**
     * 字段渲染展示
     * @param {当前字段数据} columnData
     * @param {当前行的数据} columnFormData
     * @param {所在行的$index} columnIndex
     * @param {是否只显示文本} isViewText
     * @returns
     */
    const columnViewDom = (columnData, columnFormData, columnIndex, isViewText = false) => {
      const { $bind = {}, $on = {} } = props.getColumnComponentData?.(columnData) ?? {}
      const gridParams = store.get($bind['list-code'])
      const options = gridParams?.options
      const lineEdit = gridParams.lineEdit ?? false
      const attrs = {
        ...$bind,
        'page-grid-data': props.data,
        'is-data-children': isDataChildren.value,
        options,
        row: columnFormData,
        rowIndex: columnIndex,
        'right-click-menu-arr': options?.rightClickMenuArr,
        'line-edit': lineEdit
      }
      const onAttrs = {
        ...Object.fromEntries(
          Object.keys($on).map((key) => [
            `on${key.charAt(0).toUpperCase()}${key
              .slice(1)
              .replace(/-([a-z])/g, (match, letter) => letter.toUpperCase())}`,
            $on[key]
          ])
        )
      }
      return (
        <NormalColumnContent
          isContentViewText={isViewText}
          {...attrs}
          {...onAttrs}
          class={
            'mobile-column-' +
            columnData.prop +
            '-' +
            columnIndex +
            (isValidateError(columnFormData, columnIndex, columnData) ? ' mobile_required_bg required-corner' : '')
          }
          style={isValidateError(columnFormData, columnIndex, columnData) ? 'display:block;' : ''}
        />
      )
    }

    /**
     *
     * @param {字段columns  List} layoutDatas
     * @param {当前行的数据} columnFormData
     * @param {所在行的$index} columnIndex
     * @param {限制显示字段} showFieldCount
     * @returns .filter((_, index) => !props.showFieldCount || props.showFieldCount > index + 1)
     */
    const getElDescriptions = (
      layoutDatas,
      columnFormData = detailsFormData.value,
      columnIndex = isCheckedIndex.value,
      showFieldCount = undefined
    ) => {
      // const propertyData = columnData?.find(({ property }) => property)
      return (
        <ElDescriptions
          column={1}
          label-width={mobileSuperGridLabelWidth === 'AUTO' ? undefined : maxLabelWidth.value}
          align="right"
          direction="horizontal"
          layout="form"
        >
          {(showFieldCount ? layoutDatas?.slice?.(0, showFieldCount) : layoutDatas)?.map((columnCol, index) => (
            <ElDescriptionsItem
              key={columnCol.label + index}
              v-slots={{
                label: () => <div v-html={columnCol.label ? `${columnCol.label}：` : ''} />
              }}
              // onRowDblclick={(event) => {
              //     console.log('我双击了', columnCol?.property )
              //     // if (isViewText) return
              //     event.stopPropagation()
              //     // emit('rowDblclick', columnFormData, columnData, event)
              // }}
            >
              {columnViewDom(columnCol, columnFormData, columnIndex) || '-'}
            </ElDescriptionsItem>
          ))}
        </ElDescriptions>
      )
    }

    watch(
      () => attrs.selection,
      (newValue) => {
        console.log('表格勾选数据监听', newValue)
        checkedList.value = newValue.map(({ $rowDataGuId }) => $rowDataGuId)
      },
      { deep: true }
    )

    // 勾选监听
    watch(
      checkedList,
      (newValue, oldValue) => {
        console.log(newValue, oldValue)
        if (attrs.selection.length === newValue.length) {
          if (attrs.selection.every(({ $rowDataGuId }) => newValue.includes($rowDataGuId))) return
        }
        const selectData = dataChildrenList.value.filter(({ $rowDataGuId }) => newValue?.includes($rowDataGuId))
        const findData = checkedClickId.value
          ? dataChildrenList.value.find(({ $rowDataGuId }) => checkedClickId.value === $rowDataGuId)
          : undefined
        // 新增选中
        if (newValue.length > oldValue?.length && findData) {
          emit('select', selectData, findData)
        }
        // 移除选中
        if (newValue.length < oldValue?.length && findData) {
          emit('select', selectData, findData)
        }
        emit('selectionChange', selectData)
        checkedClickId.value = undefined
      },
      { deep: true }
    )

    // 滚动数据加载监听
    watch(
      () => props.data,
      (newValue) => {
        isDataChildren.value = newValue.some((item) => Array.isArray(item?.children))
        setPaginationList(newValue)
      },
      { deep: true }
    )

    // 滚动到底部监听
    const scrollLoad = () => {
      console.log('分页', pagesNumber.value, props.currentPage)
      if (pagesNumber.value > 1 && pagesNumber.value > props.currentPage) {
        // paginationList.value[props.currentPage - 1]?.length ||
        console.log(dataList.value.length, props.pageSize * props.currentPage)
        if (dataList.value.length === props.pageSize * props.currentPage) {
          isPaginationLoading.value = true
          const currentPage = props.currentPage + 1
          console.log('开始滚动了', currentPage, pagesNumber.value)
          emit('update:current-page', currentPage)
          emit('currentChange', currentPage)
        } else {
          if (props.isSubTable) {
            isPaginationLoading.value = false
          }
          console.log('等待数据加载')
        }
      } else {
        console.log('到底了')
      }
    }

    const addFunction = (Fun) => {
      Fun?.(props.listCode).then(() => {
        // 新增行后，滚动到最底部
        emit('scrollToBottom')
      })
    }

    onUnmounted(() => {
      eventBus.$off('change-add-state')
    })

    const getAddBtn = (Fun) =>
      addColumnBtn.value && (
        <ElButton type="primary" plain icon={<CirclePlus />} onClick={() => addFunction(Fun)}>
          {t('imatrixUIPublicModel.add')}
        </ElButton>
      )

    return {
      getAddBtn,
      toggleSelectAll,
      clearSelection,
      renderDom: (AddBtn) => (
        // renderDom: () => (
        <Scrollbar
          onScrollToBottom={scrollLoad}
          flex-auto
          set-max-height={(data) => {
            if (data?.windowHeight) {
              const height = data?.windowHeight - 70
              return height > 400 ? height : 400
            }
          }}
        >
          {
            <ElDrawer
              v-model={isChildrenDrawer.value}
              modal-class="yx-drawer yx-scrollbar-body"
              with-header={true}
              direction="btt"
              append-to-body
              size="90vh"
              v-slots={{
                header: () => (
                  <div class="yx-flex-wrap" style={{ gap: '10px' }}>
                    {layoutData.value.header[0] && `${layoutData.value.header[0].label}: `}
                    <ElBreadcrumb separator-icon={<ArrowRight></ArrowRight>}>
                      {childrenBreadcrumbData.value.map((columnFormData, i) => {
                        const label = columnViewDom(layoutData.value.header[0], columnFormData, undefined, true)
                        return (
                          <ElBreadcrumbItem>
                            {childrenBreadcrumbData.value.length - 1 === i ? (
                              label
                            ) : (
                              <ElLink
                                onClick={() =>
                                  (childrenBreadcrumbData.value = childrenBreadcrumbData.value.slice(0, i + 1))
                                }
                              >
                                {label}
                              </ElLink>
                            )}
                          </ElBreadcrumbItem>
                        )
                      })}
                    </ElBreadcrumb>
                  </div>
                )
              }}
              onClosed={() => (childrenBreadcrumbData.value = [])}
            >
              <Scrollbar scrollable-main max-height="100%" style={{ flex: '1 1 auto' }}>
                <div class="yx-flex-wrap" vertical style={{ gap: isCompact ? '0px' : '15px' }}>
                  {childrenList.value.map((columnFormData, columnIndex) => {
                    // 开启编辑后禁止选中
                    const onChecked = () => !columnFormData.$editing && setCheckedList(columnFormData.$rowDataGuId)

                    // 是否选中
                    const isChecked = checkedList.value.includes(columnFormData.$rowDataGuId)

                    // 是否有子表
                    const isSubTable = props.isSubTable || !!((columnFormData?.children?.length ?? 0) > 0)
                    const clickPropertyData =
                      layoutData.value.content?.find(({ property }) => property) ?? layoutData.value.content[0]
                    // 是否启用行编辑
                    const isEnableEdit = props.isEnableEdit
                    return (
                      <CardView
                        form={columnFormData}
                        no={isIndex ? columnIndex + 1 : undefined}
                        isChecked={isChecked}
                        isSubTable={isSubTable}
                        isCheck={isCheck.value}
                        isMore={!columnFormData.$editing}
                        isShowDetailsMore={isShowDetailsMore.value}
                        isEnableEdit={isEnableEdit}
                        allRowDefaultEditable={allRowDefaultEditable}
                        onChecked={onChecked}
                        onShowSubTable={() => {
                          childrenBreadcrumbData.value = [...childrenBreadcrumbData.value, columnFormData]
                        }}
                        onRowClick={(event) => emit('rowClick', columnFormData, clickPropertyData, event)}
                        onRowDblclick={(event) => emit('rowDblclick', columnFormData, clickPropertyData, event)}
                        v-slots={{
                          titleSlot: '',
                          children: ({ isMore }) =>
                            getElDescriptions(
                              layoutData.value.content,
                              columnFormData,
                              columnIndex,
                              !isMore ? undefined : props.showFieldCount
                            ),
                          footerSlot: isShowFooter.value && (
                            <div
                              class="yx-flex-wrap"
                              wrap
                              style={{ display: 'flex', alignItems: 'center', gap: '15px' }}
                            >
                              {layoutData.value.footer?.map((columnCol) =>
                                columnViewDom(columnCol, columnFormData, columnIndex)
                              )}
                            </div>
                          )
                        }}
                      />
                    )
                  })}
                </div>
              </Scrollbar>
            </ElDrawer>
          }
          <div class="yx-flex-wrap" vertical style={{ gap: isCompact ? '0px' : '15px' }}>
            {dataList.value.length === 0 && <ElEmpty description={t('imatrixUIPublicModel.noData')}>{AddBtn}</ElEmpty>}

            {dataList.value.map((columnFormData, columnIndex) => {
              // 开启编辑后禁止选中
              const onChecked = () => !columnFormData.$editing && setCheckedList(columnFormData.$rowDataGuId)

              // 是否选中
              const isChecked = checkedList.value.includes(columnFormData.$rowDataGuId)

              // 是否有子表
              const isSubTable = props.isSubTable || !!(columnFormData?.children?.length ?? false)
              const clickPropertyData =
                layoutData.value.content?.find(({ property }) => property) ?? layoutData.value.content[0]
              // 是否启用行编辑
              const isEnableEdit = props.isEnableEdit

              if (isCompact) {
                return (
                  <CompactCard
                    row={columnFormData}
                    rowIndex={columnIndex}
                    no={isIndex.value ? columnIndex + 1 : undefined}
                    isChecked={isChecked}
                    isSubTable={isSubTable}
                    isCheck={isCheck.value}
                    isShowDetailsMore={isShowDetailsMore.value}
                    onChecked={onChecked}
                    onShowSubTable={() => {
                      childrenBreadcrumbData.value = [columnFormData]
                      isChildrenDrawer.value = true
                    }}
                    onRowClick={(event) => emit('rowClick', columnFormData, clickPropertyData, event)}
                    onRowDblclick={(event) => emit('rowDblclick', columnFormData, clickPropertyData, event)}
                    v-slots={{
                      titleSlot: () => null,
                      children: ({ isMore }) =>
                        getElDescriptions(
                          layoutData.value.content,
                          columnFormData,
                          columnIndex,
                          !isMore ? undefined : props.showFieldCount
                        ),
                      footerSlot: isShowFooter.value
                        ? () => (
                            <div
                              class="yx-flex-wrap"
                              wrap
                              style={{ display: 'flex', alignItems: 'center', gap: '18px' }}
                            >
                              {layoutData.value.footer?.map((columnCol) => (
                                <div>{columnViewDom(columnCol, columnFormData, columnIndex)}</div>
                              ))}
                            </div>
                          )
                        : undefined
                    }}
                  />
                )
              }

              return (
                <CardView
                  form={columnFormData}
                  no={isIndex.value ? columnIndex + 1 : undefined}
                  isChecked={isChecked}
                  isSubTable={isSubTable}
                  isCheck={isCheck.value}
                  isMore={!columnFormData.$editing}
                  isShowDetailsMore={isShowDetailsMore.value}
                  isEnableEdit={isEnableEdit}
                  allRowDefaultEditable={allRowDefaultEditable}
                  onChecked={onChecked}
                  onShowSubTable={() => {
                    childrenBreadcrumbData.value = [columnFormData]
                    isChildrenDrawer.value = true
                  }}
                  onRowClick={(event) => emit('rowClick', columnFormData, clickPropertyData, event)}
                  onRowDblclick={(event) => emit('rowDblclick', columnFormData, clickPropertyData, event)}
                  v-slots={{
                    titleSlot: '',
                    children: ({ isMore }) =>
                      getElDescriptions(
                        layoutData.value.content,
                        columnFormData,
                        columnIndex,
                        !isMore ? undefined : props.showFieldCount
                      ),
                    footerSlot: isShowFooter.value && (
                      <div class="yx-flex-wrap" wrap style={{ gap: '15px' }}>
                        {layoutData.value.footer?.map((columnCol) =>
                          columnViewDom(columnCol, columnFormData, columnIndex)
                        )}
                      </div>
                    )
                  }}
                />
              )
            })}

            {/* {dataList.value.length > 0 && AddBtn} */}

            {dataList.value.length > 0 && pagesNumber.value > 1 && (
              <ElDivider>
                {pagesNumber.value > props.currentPage || isPaginationLoading.value ? (
                  <ElIcon loading-rotate size={25} color="#409eff" style={{ margin: '15px auto' }}>
                    <Loading></Loading>
                  </ElIcon>
                ) : (
                  pagesNumber.value <= props.currentPage && isLoadPaginationData.value && t('imatrixUIPublicModel.noMoreData')
                )}
              </ElDivider>
            )}
          </div>
        </Scrollbar>
      )
    }
  },
  render() {
    // 为了 能兼容 使用 mixins 参数
    return this.renderDom(this.getAddBtn(this.createRow))
    // return this.renderDom()
  }
})
