<script setup lang="tsx">
import { nextTick, ref } from 'vue';
import { NButton, NPopconfirm, NTag } from 'naive-ui';
import type { InternalRowData } from 'naive-ui/es/data-table/src/interface';
import { yesOrNoRecord } from '@/constants/common';
import { menuTypeRecord } from '@/constants/business';
import { fetchAddMenu, fetchDelMenu, fetchEditMenu, fetchGetMenuList } from '@/service/api';
import { useAppStore } from '@/store/modules/app';
import { buildMenuTree } from '@/utils/zt';
import { $t } from '@/locales';
import SvgIcon from '@/components/custom/svg-icon.vue';
import { useForm } from '@/components/zt/Form/hooks/useForm';
import { type OperateType } from './modules/menu-operate-modal.vue';
import { formSchems } from './modules/shared';
const appStore = useAppStore();
const checkedRowKeys = ref([]);

const wrapperRef = ref<HTMLElement | null>(null);
const menusData = ref([]);
const loading = ref(false);
const showModal = ref(false);
const formLoading = ref(false);

const [registerForm, { setFieldsValue, validate, getFieldsValue, updateSchema }] = useForm({
  schemas: formSchems,
  showSubmitButton: false,
  showAdvancedButton: false,
  showResetButton: false,
  labelWidth: 120,
  showActionButtonGroup: false,
  layout: 'horizontal',
  gridProps: {
    cols: '1',
    itemResponsive: true
  },
  collapsedRows: 1
});

const colums: NaiveUI.TableColumn<InternalRowData>[] = [
  {
    type: 'selection',
    align: 'center',
    width: 48
  },
  {
    key: 'id',
    title: $t('page.manage.menu.id'),
    align: 'center'
  },
  {
    key: 'type',
    title: $t('page.manage.menu.menuType'),
    align: 'center',
    width: 80,
    render: (row: InternalRowData) => {
      const tagMap: Record<Api.SystemManage.MenuType, NaiveUI.ThemeColor> = {
        0: 'default',
        1: 'primary',
        2: 'error'
      };

      const type = row.type as keyof typeof menuTypeRecord;
      const label = $t(menuTypeRecord[type]);
      return <NTag type={tagMap[type]}>{label}</NTag>;
    }
  },
  {
    key: 'name',
    title: $t('page.manage.menu.menuName'),
    align: 'center',
    minWidth: 120,
    render: (row: InternalRowData) => {
      return <span>{row.name}</span>;
    }
  },
  {
    key: 'icon',
    title: $t('page.manage.menu.icon'),
    align: 'center',
    width: 60,
    render: (row: InternalRowData) => {
      return (
        <div class="flex-center">
          <SvgIcon icon={String(row.icon)} class="text-icon" />
        </div>
      );
    }
  },
  {
    key: 'routeName',
    title: $t('page.manage.menu.routeName'),
    align: 'center',
    minWidth: 120
  },
  {
    key: 'url',
    title: $t('page.manage.menu.routePath'),
    align: 'center',
    minWidth: 120
  },
  {
    key: 'hideInMenu',
    title: $t('page.manage.menu.hideInMenu'),
    align: 'center',
    width: 80,
    render: (row: InternalRowData) => {
      const hide: CommonType.YesOrNo = row.hideInMenu ? 'Y' : 'N';

      const tagMap: Record<CommonType.YesOrNo, NaiveUI.ThemeColor> = {
        Y: 'error',
        N: 'default'
      };

      const label = $t(yesOrNoRecord[hide]);

      return <NTag type={tagMap[hide]}>{label}</NTag>;
    }
  },
  {
    key: 'parentId',
    title: $t('page.manage.menu.parentId'),
    width: 90,
    align: 'center'
  },
  {
    key: 'orderNum',
    title: $t('page.manage.menu.order'),
    align: 'center',
    width: 60
  },
  {
    key: 'operate',
    title: $t('common.operate'),
    align: 'center',
    width: 230,
    fixed: 'right',
    render: (row: any) => (
      <div class="flex-center justify-end gap-8px">
        {row.type == '0' && (
          <NButton type="primary" ghost size="small" onClick={() => handleAddChildMenu(row)}>
            {$t('page.manage.menu.addChildMenu')}
          </NButton>
        )}
        <NButton type="primary" ghost size="small" onClick={() => handleEdit(row)}>
          {$t('common.edit')}
        </NButton>
        <NPopconfirm onPositiveClick={() => handleDelete(row.menuId)}>
          {{
            default: () => $t('common.confirmDelete'),
            trigger: () => (
              <NButton type="error" ghost size="small" loading={formLoading.value}>
                {$t('common.delete')}
              </NButton>
            )
          }}
        </NPopconfirm>
      </div>
    )
  }
];

// const { checkedRowKeys, onBatchDeleted, onDeleted } = useTableOperate(data, 'id', getData);

const operateType = ref<OperateType>('add');

function handleAdd() {
  operateType.value = 'add';
  showModal.value = true;
}

async function handleBatchDelete() {
  // request
  // console.log(checkedRowKeys.value);
}

async function handleDelete(id: number) {
  // request
  // console.log(id);
  formLoading.value = true;
  await fetchDelMenu(id);
  init();
  formLoading.value = false;
}

function handleEdit(item: Api.SystemManage.Menu) {
  showModal.value = true;
  operateType.value = 'edit';
  nextTick(async () => {
    await setFieldsValue(item);
    updateSchema([{ field: 'type', componentProps: { disabled: true } }]);
  });
}

function handleAddChildMenu(item: any) {
  operateType.value = 'addChild';
  showModal.value = true;
  nextTick(() => {
    setFieldsValue({ parentId: item.menuId, url: item.url });
  });
}

async function getAllPages() {
  const { data } = await fetchGetMenuList();
  const menuData = buildMenuTree(data);
  menusData.value = menuData;
}

function init() {
  getAllPages();
}

// init
init();

async function handleSubmit() {
  await validate();
  formLoading.value = true;
  const form = getFieldsValue();
  if (operateType.value == 'add' || operateType.value == 'addChild') {
    await fetchAddMenu(form as Api.SystemManage.AddMenu);
    formLoading.value = false;
    showModal.value = false;

    init();
  } else {
    await fetchEditMenu(form as Api.SystemManage.AddMenu);
    formLoading.value = false;
    showModal.value = false;
    init();
  }
}
</script>

<template>
  <div ref="wrapperRef" class="flex-col-stretch gap-16px overflow-hidden lt-sm:overflow-auto">
    <NCard :title="$t('page.manage.menu.title')" :bordered="false" size="small" class="card-wrapper sm:flex-1-hidden">
      <template #header-extra>
        <TableHeaderOperation
          :disabled-delete="checkedRowKeys.length === 0"
          :loading="loading"
          is-add
          @add="handleAdd"
          @delete="handleBatchDelete"
          @refresh="init"
        />
      </template>
      <NDataTable
        v-model:checked-row-keys="checkedRowKeys"
        :columns="colums"
        :data="menusData"
        size="small"
        :flex-height="!appStore.isMobile"
        :scroll-x="1088"
        :loading="loading"
        :row-key="row => row.menuId"
        remote
        class="sm:h-full"
      />
      <!--
 <MenuOperateModal
        v-model:visible="visible"
        :operate-type="operateType"
        :row-data="editingData"
        :all-pages="allPages"
      />

-->
      <NModal v-model:show="showModal">
        <NCard class="w-800px">
          <template #header>
            <div>
              {{ operateType == 'add' ? '新增菜单' : operateType == 'addChild' ? '新增子菜单' : ' 编辑菜单' }}
            </div>
          </template>
          <BasicForm @register-form="registerForm">
            <template #parentId="{ model, field }">
              <NTreeSelect
                v-model:value="model[field]"
                :options="menusData"
                label-field="name"
                key-field="menuId"
              ></NTreeSelect>
            </template>
          </BasicForm>
          <template #footer>
            <div class="flex justify-end">
              <NButton class="mr-3" @click="showModal = false">取消</NButton>
              <NButton type="primary" :loading="formLoading" @click="handleSubmit">确定</NButton>
            </div>
          </template>
        </NCard>
      </NModal>
    </NCard>
  </div>
</template>

<style scoped></style>
