/**version-1.0*/
let modules = {};
import Sortable from "sortablejs";
import tableConfig from "./config.js";
import customConfig from "./customConfig.js";
import Vue from "vue";
import { extendDeeply } from "../../utils/index.js";
import corejsConfig from "@/corejsConfig";
import settingConfig from "@/settings.js";
import { getCellValue, createParams } from "./util/index";

let configUtil = {
  Sortable,
  extendDeeply,
  tableConfig,
  Vue,
};

function getGrid(that, tableRef) {
  let $grid;
  if (Array.isArray(that.$refs[tableRef])) {
    $grid = that.$refs[tableRef][0];
  } else {
    $grid = that.$refs[tableRef];
  }
  return $grid;
}

/** 是否在列子树中包含目标叶子列（同级 ref 优先，兜底 id） */
function columnSubtreeContainsLeaf(node, leaf) {
  if (!node || !leaf) return false;
  if (node === leaf) return true;
  if (leaf.id && node.id && String(node.id) === String(leaf.id)) return true;
  if (node.children && node.children.length) {
    return node.children.some((child) =>
      columnSubtreeContainsLeaf(child, leaf)
    );
  }
  return false;
}

/** leaf 所属的 collectColumn 最顶层节点的下标（-1 表示未找到） */
function collectTopRootIndex(collectColumn, leaf) {
  if (!collectColumn || !collectColumn.length || !leaf) return -1;
  return collectColumn.findIndex((root) =>
    columnSubtreeContainsLeaf(root, leaf)
  );
}

async function initVxeTable(option) {
  let tableName = option.tableName;
  if (
    !configUtil.tableConfig.disableTableName &&
    option.tableNameRequired !== false &&
    !tableName &&
    settingConfig.tableStorageDisabled !== true
  ) {
    return false;
  }

  let that = option.vue;
  if (!that.$refs[option.tableRef]) {
    await that.$nextTick();
  }
  let $grid = getGrid(that, option.tableRef);
  if (!$grid) {
    return false;
  }
  delete option.vue;

  //操作列自动补全
  handleCustomAlign(option);

  initColumnIndex(option.columns);

  let originOption = that.$baseLodash.cloneDeep(option);
  originOption.vue = that;
  $grid.originOption = originOption;
  option.vue = that;

  let isQueryAllPage = true;
  if (option.isQueryAllPage !== null && option.isQueryAllPage !== undefined) {
    isQueryAllPage = option.isQueryAllPage;
  }

  let searchColumns = null;
  if (tableName) {
    $grid.tableName = tableName;
    if (option.path) {
      await getTableData(that, option.tableRef, "isQueryAllPage", (res1) => {
        let result = res1.objx ? res1.objx.data : null;
        if (result !== null && result !== undefined) {
          if (result === "false" || result === false) {
            isQueryAllPage = false;
          } else {
            isQueryAllPage = true;
          }
        }
      });
    }
    await getTableJson(tableName, that, (resultMsg) => {
      let objx = resultMsg.objx;
      if (objx !== null && objx !== undefined) {
        let jsonStr = objx.data;
        if (jsonStr) {
          let json = JSON.parse(decodeURIComponent(jsonStr));
          let columnData = json.columns ? json.columns : json;
          if (columnData) {
            option.columns = initColumn(option, columnData);
          }
          searchColumns = initSearchColumns(
            option.searchColumns,
            json.searchColumns
          );
          $grid.searchColumns = searchColumns;
          initExportColumns($grid, json);
        }
      }
      if (!searchColumns || !searchColumns.length) {
        searchColumns = initSearchColumns(option.searchColumns);
        $grid.searchColumns = searchColumns;
      }
    });
  } else {
    searchColumns = initSearchColumns(option.searchColumns);
    $grid.searchColumns = searchColumns;
  }

  if (!!$grid?.$refs?.xTable) {
    $grid.$refs.xTable.getCellValue = getCellValue;
    $grid.$refs.xTable.createParams = createParams;
  }

  // $grid.getCellValue = getCellValue;
  // $grid.createParams = createParams;

  option.isQueryAllPage = isQueryAllPage;
  let nOption = initOption(option);

  // $grid.isQueryAllPage = isQueryAllPage;

  if (tableName) {
    nOption.tableName = tableName;
  }

  nOption.vue = that;
  //绑定列位置拖拽
  columnDrop(that, tableName, option.tableRef);

  //自动绑定toobar
  handleToolbar($grid, option);

  // nOption.originOption = originOption;
  // nOption.getCellValue = getCellValue;
  // nOption.createParams = createParams;
  // nOption.isQueryAllPage = isQueryAllPage;
  // nOption.searchColumns = searchColumns;
  let params = {
    originOption,
    getCellValue,
    createParams,
    isQueryAllPage,
    searchColumns,
  };
  if (!nOption.params) nOption.params = {};
  Object.assign(nOption.params, params);
  return nOption;
}

//自动绑定toobar
function handleToolbar($grid, option) {
  let selfConfig = getSelfConfig();
  if (
    option.bindToolbar ||
    (option.bindToolbar !== false && selfConfig.bindToolbar)
  ) {
    let loopDo = function (children) {
      if (children && children.length) {
        children.forEach((item) => {
          if (item.$options.name === "VxeToolbar") {
            $grid.connect(item);
          } else {
            loopDo(item.$children);
          }
        });
      }
    };
    that.$nextTick(() => {
      loopDo($grid.$children);
    });
  }
}

//操作列自动补全
function handleCustomAlign(option) {
  let selfConfig = getSelfConfig();
  // let customAlign = option.customAlign || selfConfig.customAlign || "right";
  let customAlign =
    selfConfig.customAlign === false
      ? false
      : selfConfig.customAlign || "right";
  customAlign =
    option.customAlign === false ? false : option.customAlign || customAlign;

  let customColumnWidth =
    option.customColumnWidth || selfConfig.customColumnWidth || 47;
  let checkBoxColumnWidth =
    option.checkBoxColumnWidth || selfConfig.checkBoxColumnWidth || 48;

  let checkBoxRequired = selfConfig.checkBoxRequired !== false;
  if (option.checkBoxRequired === false) {
    checkBoxRequired = false;
  }

  let columnSize = option.columns.length;
  if (columnSize > 0) {
    if (checkBoxRequired) {
      let firstColumn = option.columns[0];
      if (firstColumn.type !== "checkbox") {
        option.columns.splice(0, 0, {
          type: "checkbox",
          width: checkBoxColumnWidth,
          resizable: false,
          fixed: "left",
        });
      }
    }
    if (customAlign !== false) {
      let lastColumn = option.columns[columnSize - 1];
      if (customAlign === "left") {
        if (!lastColumn.field && lastColumn.fixed === "right") {
          option.columns.splice(columnSize - 1, 1);
          lastColumn.fixed = "left";
          option.columns.splice(1, 0, lastColumn);
        } else if (columnSize > 1) {
          if (option.columns[1].field) {
            option.columns.splice(1, 0, {
              width: customColumnWidth,
              fixed: "left",
              title: "",
              sortable: false,
            });
          }
        }
      } else if (customAlign === "right") {
        let column1 = option.columns[1];
        if (!column1.field && column1.fixed === "left") {
          option.columns.splice(1, 1);
          column1.fixed = "right";
          option.columns.push(column1);
        } else if (lastColumn.field || lastColumn.fixed !== "right") {
          option.columns.push({
            width: customColumnWidth,
            fixed: "right",
            title: "",
            sortable: false,
          });
        }
      }
    }
  }
}

//列位置拖拽
function columnDrop(t, tableName, tableRef) {
  let that = t;
  const $table = getGrid(that, tableRef);
  if (!$table) {
    return;
  }
  // if (!$table.params) $table.params = {};
  if ($table.sortable) {
    $table.sortable.destroy();
    $table.sortable = null;
  }
  let dragStartIndex = -1;
  let dragEndIndex = -1;
  $table.sortable = configUtil.Sortable.create(
    $table.$el.querySelector(
      ".body--wrapper>.vxe-table--header .vxe-header--row"
    ),
    {
      handle: ".vxe-header--column:not(.col--fixed)",
      onMove: (a, b, c) => {
        let { dragged, related } = a;
        // dragStartIndex = getElementIndex(dragged);
        // dragEndIndex = getElementIndex(related);

        let tableColumn = $table.getTableColumn().tableColumn;
        let draggedColId = dragged.getAttribute("colid");
        let relatedColId = related.getAttribute("colid");
        dragStartIndex = tableColumn.findIndex(
          (item) => item.id === draggedColId
        );
        dragEndIndex = tableColumn.findIndex(
          (item) => item.id === relatedColId
        );
      },
      onEnd: (dropParam) => {
        let { item } = dropParam;
        let oldIndex = dragStartIndex;
        let newIndex = dragEndIndex;

        if (newIndex < 0) newIndex = dropParam.newIndex;
        const { fullColumn, tableColumn, collectColumn } =
          $table.getTableColumn();
        const targetThElem = item;
        const wrapperElem = targetThElem.parentNode;
        let oldColumn = tableColumn[oldIndex];
        let oldTitle = oldColumn.title;

        const newColumn = tableColumn[newIndex];
        if (!newColumn) return;
        let newTitle = newColumn.title;
        if (newColumn.fixed) {
          // 错误的移动
          if (newIndex > oldIndex) {
            wrapperElem.insertBefore(
              targetThElem,
              wrapperElem.children[oldIndex]
            );
          } else {
            wrapperElem.insertBefore(
              wrapperElem.children[oldIndex],
              targetThElem
            );
          }
          return;
          /* return that.$XModal.message({
          content: '固定列不允许拖动！',
          status: 'error'
        }) */
        }
        // 叶子在 fullColumn 中的下标，与 collectColumn 顶层结构的下标不能直接混用
        const oldColumnIndex = fullColumn.findIndex(
          (item) => item.id === oldColumn.id
        );
        const newColumnIndex = fullColumn.findIndex(
          (item) => item.id === newColumn.id
        );
        const oldLeafColumn = fullColumn[oldColumnIndex];
        const newLeafColumn = fullColumn[newColumnIndex];
        let oldLeafTitle = oldLeafColumn.title;
        let newLeafTitle = newLeafColumn.title;
        if (oldColumnIndex === newColumnIndex) {
          return;
        }
        const oldTopIdx = collectTopRootIndex(collectColumn, oldLeafColumn);
        const newTopIdx = collectTopRootIndex(collectColumn, newLeafColumn);
        if (oldTopIdx === -1 || newTopIdx === -1) {
          return;
        }
        if (oldTopIdx !== newTopIdx) {
          let oldTopColumn = collectColumn[oldTopIdx];
          let newTopColumn = collectColumn[newTopIdx];
          let oldTopTitle = oldTopColumn.title;
          let newTopTitle = newTopColumn.title;
          const currRow = collectColumn.splice(oldTopIdx, 1)[0];
          collectColumn.splice(newTopIdx, 0, currRow);
          $table.loadColumn(collectColumn);
          addTableJson(that, $table, tableName, collectColumn);
        }
      },
    }
  );
}

function getSelfConfig() {
  let tableConfig = configUtil.tableConfig || {};
  let selfConfig = tableConfig.selfConfig || {};
  return selfConfig;
}

function initColumnDefaulAttrs(columns, opts) {
  let tableConfig = configUtil.tableConfig || {};
  let selfConfig = getSelfConfig();
  let lockCheckboxWidth =
    opts.lockCheckboxWidth !== false
      ? opts.lockCheckboxWidth || selfConfig.lockCheckboxWidth
      : null;
  let filterType =
    opts.filterType !== false && !opts.treeNodeUrl
      ? opts.filterType || selfConfig.filterType || "filterContent"
      : null;
  let sortAll =
    opts.sortAll === true || (opts.sortAll !== false && !opts.treeNodeUrl);

  columns.forEach((column) => {
    // 只有最底层的列（没有 children）才设置默认属性
    if (!column.children || column.children.length === 0) {
      // 设置 sortable
      if (
        sortAll &&
        column.title &&
        (column.sortable === null || column.sortable === undefined)
      ) {
        column.sortable = true;
      }

      // 设置过滤器
      if (filterType && column.title && column.field) {
        if (
          column.filterType === "filterContent" ||
          ((column.filterType === null || column.filterType === undefined) &&
            filterType === "filterContent")
        ) {
          if (!column.filters) {
            column.filters = [
              {
                data: {},
              },
            ];
          }
          if (!column.filterRender) {
            column.filterRender = {
              name: "FilterContent",
            };
          }
        } else if (
          column.filterType === "filterInput" ||
          ((column.filterType === null || column.filterType === undefined) &&
            filterType === "filterInput")
        ) {
          if (!column.filters) {
            column.filters = [
              {
                data: "",
              },
            ];
          }
          if (!column.filterRender) {
            column.filterRender = {
              name: "FilterInput",
            };
          }
        }
      }

      // 设置复选框列宽度
      if (lockCheckboxWidth && column.type === "checkbox") {
        column.width = lockCheckboxWidth;
      }
    } else {
      column.sortable = false;
      column.filterType = false;
      column.align = "center";
      column.resizable = false;
      // 递归处理 children
      initColumnDefaulAttrs(column.children, opts);
    }
  });
}

function initOption(opts) {
  let result = {};
  let that = opts.vue;
  let $grid = getGrid(that, opts.tableRef);

  let path = opts.path || "";
  // let columns = JSON.parse(JSON.stringify(opts.columns || []));
  let columns = opts.columns || [];
  let isQueryAllPage = opts.isQueryAllPage;
  let pagerLayouts = getPagerConfigLayouts(opts);

  let config = opts.config || {};

  initColumnDefaulAttrs(columns, opts);

  let defaultOptions = {
    columnKey: true,
    resizable: true,
    showOverflow: true,
    showHeaderOverflow: true,
    showFooterOverflow: true,
    highlightHoverRow: true,
    border: "inner",
    height: "auto",
    // maxHeight:"1000px",
    // rowId: 'id',
    emptyText: " ",
    sortConfig: {
      trigger: "cell",
      remote: false,
    },
    filterConfig: {
      remote: false,
    },
    pagerConfig: {
      autoHidden: true,
      perfect: true,
      pageSize: 200,
      pageSizes: [50, 100, 200, 500],
      layouts: pagerLayouts,
      slots: {
        left: (obj, b, c) => {
          let $grid = obj.$grid;
          let k = $grid.$data;
          let tableDataInfo = $grid.getTableData();
          let data = tableDataInfo.fullData;
          let h = $grid.$createElement;

          let proxyInfo = $grid.getProxyInfo();
          let pager = proxyInfo ? proxyInfo.pager : null;

          let celems = [
            h("span", $grid.$t2("本页记录数", "components.table.currentNum")),
            h(
              "span",
              {
                attrs: {
                  class: "f-red",
                },
              },
              " " + tableDataInfo.visibleData.length + " "
            ),
          ];
          if (pager && $grid.isQueryAllPage) {
            celems.push(
              h(
                "span",
                "，" + $grid.$t2("总记录数", "components.table.totalNum")
              )
            );
            celems.push(
              h(
                "span",
                {
                  attrs: {
                    class: "f-red",
                  },
                },
                " " + pager.total + " "
              )
            );
          }
          let elem = h("span", {}, celems);
          return [elem];
        },
      },
    },
    exportConfig: {
      // 默认选中类型
      type: "xlsx",
      // 局部自定义类型
      types: ["xlsx", "csv", "html", "xml", "txt"],
      // 自定义数据量列表
      modes: ["current", "all"],
    },
    radioConfig: {
      labelField: "id",
      reserve: true,
      highlight: true,
    },
    checkboxConfig: {
      highlight: true,
    },
    customConfig: {
      storage: false,
    },
    scrollX: {
      // enabled: true,
      gt: 10,
      // oSize: 5
    },
    /*loadingConfig: {
      icon: "vxe-loading--spinner",
      text: ' '
    },*/
    columns: columns,
  };
  let tableDefaultConfig =
    corejsConfig?.componentConfig?.table?.defaultConfig || {};
  defaultOptions = configUtil.extendDeeply(defaultOptions, tableConfig);
  defaultOptions = configUtil.extendDeeply(defaultOptions, customConfig);
  defaultOptions = configUtil.extendDeeply(defaultOptions, tableDefaultConfig);

  if (opts.path) {
    // defaultOptions.filterInput = true;
    defaultOptions.pagerConfig.autoHidden = false;
    defaultOptions.proxyConfig = {
      seq: true, // 启用动态序号代理
      sort: true, // 启用排序代理
      filter: true, // 启用筛选代理
      props: {
        result: "objx.records", // 配置响应结果列表字段
        total: "objx.total", // 配置响应结果总页数字段
      },
      ajax: {
        // 接收 Promise 对象
        query: ({ page, sorts, filters, form }) => {
          if (!opts.path) {
            return;
          }
          return new Promise((resolve, reject) => {
            let toDo = () => {
              let formData = opts.param ? opts.param() || {} : {};
              const queryParams = Object.assign({}, formData);

              // 处理排序条件
              /*const firstSort = sorts[0];
              if (firstSort) {
                queryParams.sort = firstSort.property;
                queryParams.order = firstSort.order;
              }*/
              // 处理筛选条件
              filters.forEach(({ property, values }) => {
                queryParams[property] = values.join(",");
              });
              if (page.pageSize !== undefined) {
                queryParams["size"] = page.pageSize;
                queryParams["current"] = page.currentPage;
              }

              let $grid = getGrid(that, opts.tableRef);
              let isQueryAllPage = $grid.isQueryAllPage;
              let pathStr1 = "";
              if (isQueryAllPage === false) {
                queryParams.searchCount = false;
              }

              let reqPath = typeof path === "function" ? path() : path;
              let addUserForTableEnabled =
                settingConfig.addUserForTableDisabled !== true;
              let addCreateInfo =
                opts.addCreateInfo === true || addUserForTableEnabled;
              let queryCreateInfo =
                opts.queryCreateInfo === true || addUserForTableEnabled;
              let reqData = queryParams;
              if (opts.paramHandle) {
                reqData = opts.paramHandle
                  ? opts.paramHandle(queryParams) || {}
                  : {};
              }
              that.$commonHttp({
                aes: opts.aes || false,
                url: reqPath,
                method: "post",
                data: reqData,
                addCreateInfo: addCreateInfo,
                queryCreateInfo: queryCreateInfo,
                callback: (res) => {
                  resolve(res);
                  if (res.type === "success") {
                    let rows = res.objx
                      ? res.objx.records || res.objx || []
                      : [];
                    if (opts.treeNodeUrl) {
                      if (rows.length > 0) {
                        let $t = getGrid(that, opts.tableRef);
                        let treeConditions = $t.params.originOption
                          .treeConditions || ["enabled"];
                        let treeFiled = Object.keys(formData).some((key) => {
                          return (
                            !treeConditions.includes(key) &&
                            formData[key] !== null &&
                            formData[key] !== undefined &&
                            formData[key] !== ""
                          );
                        });
                        if (treeFiled) {
                          that.$nextTick(() => {
                            setTimeout(function () {
                              let isLazy = $t.treeConfig.lazy;
                              $t.treeConfig.lazy = false;
                              $t.setAllTreeExpand(true).then(() => {
                                let fullAllDataRowMap =
                                  $t.$refs.xTable.fullAllDataRowMap;
                                let fullData = $t.getTableData().fullData;
                                fullData.forEach((lineData) => {
                                  if (
                                    $t.$refs.xTable.isTreeExpandByRow(lineData)
                                  ) {
                                    let rest = fullAllDataRowMap.get(lineData);
                                    rest.treeLoaded = true;
                                  }
                                });
                                $t.treeConfig.lazy = isLazy;
                              });
                            }, 0);
                          });
                        } else {
                          let row = rows[0];
                          if (row[result.treeConfig.hasChild]) {
                            that.$nextTick(() => {
                              setTimeout(function () {
                                $t.setTreeExpand(row, true);
                              }, 0);
                            });
                          }
                        }
                      }
                    }
                    if (opts.callback) {
                      that.$nextTick(() => {
                        setTimeout(function () {
                          opts.callback(rows, res);
                        }, 0);
                      });
                    }
                  }
                },
                error: (error) => {
                  reject(error);
                },
              });
            };
            let index = 0;
            let loopHandle = () => {
              if (index < 500 && $grid.tableFormStop === true) {
                //阻塞列表查询，或者次数达到500时，自动释放
                index++;
                setTimeout(() => {
                  loopHandle();
                }, 10);
              } else {
                if ($grid.tableFormStop) $grid.tableFormStop = false;
                toDo();
              }
            };
            loopHandle();
          });
        },
        // 被某些特殊功能所触发，例如：导出数据 mode=all 时，会触发该方法并对返回的数据进行导出
        queryAll: () => fetch(path || "").then((response) => response.json()),
      },
    };
    /*defaultOptions.scrollX = {
      enabled: true,
      gt: 20
    };*/
    defaultOptions.scrollY = {
      // enabled: false,
      gt: 20,
      oSize: 20,
    };
  } else {
    if (!$grid.height && (!opts.config || !opts.config.height)) {
      defaultOptions.maxHeight = "528px";
    }
    defaultOptions.scrollY = {
      // enabled: false,
      gt: 20,
      oSize: 20,
    };
  }

  if (opts.editSaveUrl) {
    (defaultOptions.keepSource = true),
      (defaultOptions.editConfig = {
        trigger: "manual",
        mode: "row",
        showStatus: true,
        autoClear: false,
      });
  }
  if (opts.treeNodeUrl) {
    defaultOptions.proxyConfig.props.result = "objx";
    defaultOptions.pagerConfig.autoHidden = true;
    defaultOptions.treeConfig = {
      lazy: true,
      children: "children",
      hasChild: "hasChild", // 设置是否有子节点标识
      parentField: "parent",
      transform: true,
      loadMethod({ $table, row }) {
        // 模拟后台接口
        return new Promise((resolve, reject) => {
          let treeNodeParam = opts.treeNodeParam
            ? opts.treeNodeParam(row) || {}
            : {
                parent: row.id,
              };
          that.$http({
            aes: opts.aes || false,
            url: opts.treeNodeUrl,
            method: "post",
            data: treeNodeParam,
            callback: (res) => {
              if (res.type === "success") {
                // let rows = res.objx || [];
                let rows = res.objx ? res.objx.records || res.objx || [] : [];
                let hasChildField = $grid.treeConfig.hasChild;
                if (row[hasChildField] && !rows.length) {
                  row[hasChildField] = false;
                }
                resolve(rows);
                if (opts.treeCallback) {
                  that.$nextTick(() => {
                    setTimeout(function () {
                      opts.treeCallback(rows, res);
                    }, 0);
                  });
                }
              } else {
                reject(res);
              }
            },
          });
        });
      },
    };
  }

  result = configUtil.extendDeeply(defaultOptions, config);

  let pageSize = result.pagerConfig.pageSize;
  let pageSizes = result.pagerConfig.pageSizes;
  if (pageSizes && !pageSizes.includes(pageSize)) {
    for (let i = 0; i < pageSizes.length; i++) {
      let item = pageSizes[i];
      if (item > pageSize) {
        pageSizes.splice(i, 0, pageSize);
        break;
      }
    }
  }

  return result;
}

function getTableJson(tableName, that, success) {
  if (
    configUtil.tableConfig.disableTableName ||
    settingConfig.tableStorageDisabled
  )
    return false;
  if (!tableName) return;
  let url = USER_PREFIX + "/table_column/getTableJson";
  let data = {
    tableName: tableName,
  };
  let json = null;
  return that.$http({
    url: url,
    method: "post",
    data: data,
    success: success,
  });
}

function addTableExportJson() {}

function addTableJson(that, $grid, tableName, columns, success) {
  if (
    configUtil.tableConfig.disableTableName ||
    settingConfig.tableStorageDisabled
  )
    return false;
  if (!tableName) return;
  if (!columns) {
    columns = $grid.getTableColumn().collectColumn;
  }
  let saveColumn = [];
  columns.forEach(function (item, index) {
    let columnData = {
      field: item.field || item.property,
      title: item.title,
      visible: item.visible,
      width: item.renderWidth || item.width,
    };

    // 如果有 children，递归处理
    if (item.children && item.children.length > 0) {
      columnData.children = processChildren(item.children);
    }

    saveColumn.push(columnData);
  });

  // 处理 children 的递归函数
  function processChildren(children) {
    let result = [];
    children.forEach(function (childItem) {
      let childData = {
        field: childItem.field || childItem.property,
        title: childItem.title,
        visible: childItem.visible,
        width: childItem.renderWidth || childItem.width,
      };

      // 递归处理嵌套的 children
      if (childItem.children && childItem.children.length > 0) {
        childData.children = processChildren(childItem.children);
      }

      result.push(childData);
    });
    return result;
  }

  let searchColumns = $grid.params.searchColumns || [];
  let jsonData = {
    columns: saveColumn,
    searchColumns: searchColumns,
  };
  if ($grid.exportColumns && $grid.exportColumns.length) {
    jsonData.exportColumns = $grid.exportColumns;
  }
  if ($grid.exportItemColumns && $grid.exportItemColumns.length) {
    jsonData.exportItemColumns = $grid.exportItemColumns;
  }
  console.log("jsonData", jsonData);
  let json = encodeURIComponent(JSON.stringify(jsonData));

  let url = USER_PREFIX + "/table_column/addTableJson";
  let data = {
    tableName: tableName,
    // json: encodeURIComponent(JSON.stringify(saveColumn)),
    json: json,
  };
  that.$http({
    url: url,
    method: "post",
    data: data,
    success: success,
  });
}

function initColumnIndex(columns) {
  columns.forEach(function (column, index) {
    if (!column.params) column.params = {};
    if (column.params) {
      column.params._index = index;
      column.params._visible = column.visible ?? true;
    }
    if (column.children && column.children.length > 0) {
      initColumnIndex(column.children);
    }
  });
}

function initColumn(option, syncColumns) {
  let oldColumns = option.columns;
  let newColumns = [];
  if (syncColumns) {
    // 按列对象配对：DB 里同 field 多行时不得反复匹配同一 oldColumn；old 删了重复列时多余 sync 行应丢弃
    const matchedOld = new Set();
    syncColumns.forEach(function (syncColumn) {
      const field = syncColumn.field;
      if (!field) return;
      const oldColumn = oldColumns.find(function (oc) {
        return oc.field === field && !matchedOld.has(oc);
      });
      if (!oldColumn) return;
      matchedOld.add(oldColumn);
      if (!oldColumn.params) oldColumn.params = {};
      const visibleSync =
        option.visibleSync !== false && oldColumn.visibleSync !== false;
      if (visibleSync) {
        oldColumn.visible = syncColumn.visible;
      }
      if (oldColumn.width !== undefined) {
        oldColumn.params._width = oldColumn.width;
      }
      if (syncColumn.width) oldColumn.width = syncColumn.width;
      newColumns.push(oldColumn);
    });
    oldColumns.forEach(function (oldColumn, index) {
      if (matchedOld.has(oldColumn)) return;
      newColumns.splice(index, 0, oldColumn);
    });

    // 处理 children 中的列
    if (syncColumns.length > 0) {
      newColumns.forEach(function (newColumn) {
        if (newColumn.children && newColumn.children.length > 0) {
          // 在 syncColumns 中查找对应的父列
          let syncParentColumn = syncColumns.find(function (syncCol) {
            return syncCol.field === newColumn.field;
          });
          if (
            syncParentColumn &&
            syncParentColumn.children &&
            syncParentColumn.children.length > 0
          ) {
            // 递归处理 children
            newColumn.children = initColumn(
              { columns: newColumn.children },
              syncParentColumn.children
            );
          }
        }
      });
    }
  } else {
    newColumns = oldColumns;
  }
  return newColumns;
}

function initExportColumns($grid, json) {
  if (json?.exportColumns?.length) {
    $grid.exportColumns = json.exportColumns;
  }
  if (json?.exportItemColumns?.length) {
    $grid.exportItemColumns = json.exportItemColumns;
  }
}

function initSearchColumns(oriColumns, syncColumns) {
  let oldColumns = oriColumns || [];
  let newColumns = [];
  if (syncColumns) {
    const matchedOld = new Set();
    syncColumns.forEach(function (syncColumn) {
      const field = syncColumn.field;
      if (!field) return;
      const oldColumn = oldColumns.find(function (oc) {
        return oc.field === field && !oc.fixed && !matchedOld.has(oc);
      });
      if (!oldColumn) return;
      matchedOld.add(oldColumn);
      oldColumn.common = syncColumn.common || false;
      if (syncColumn.defaultValue !== undefined) {
        oldColumn.defaultValue = syncColumn.defaultValue;
      }
      newColumns.push(oldColumn);
    });
    oldColumns.forEach(function (oldColumn, index) {
      if (oldColumn.fixed) {
        newColumns.splice(index, 0, oldColumn);
        return;
      }
      if (matchedOld.has(oldColumn)) return;
      newColumns.splice(index, 0, oldColumn);
    });
  } else {
    newColumns = oldColumns;
  }
  return newColumns.length ? newColumns : oldColumns;
}

function onColumnWitchChange(option) {
  let that = option.$grid.$parent;
  let $grid = option.$grid;
  let originOption = $grid.params.originOption;
  let tableName = originOption.tableName;
  if (tableName) {
    // let columns = $grid.columns;
    const { fullColumn, tableColumn } = $grid.getTableColumn();
    addTableJson(that, $grid, tableName);
  }
}

function restoreColumnPosition(currentColumns) {
  // 根据 params._index 排序 currentColumns
  let sortedColumns = [...currentColumns].sort((a, b) => {
    let indexA = a.params?._index ?? 0;
    let indexB = b.params?._index ?? 0;
    return indexA - indexB;
  });
  console.log("sortedColumns", sortedColumns);

  // 递归处理 children
  sortedColumns.forEach((column) => {
    if (column.children && column.children.length > 0) {
      column.children = restoreColumnPosition(column.children);
    } else {
      column.visible = column.params?._visible ?? true;
      if (column.params?._width !== undefined) {
        column.width = column.params?._width;
      } else {
        // delete column.width;
      }
    }
  });

  return sortedColumns;
}

function customHandle(option) {
  let that = option.$grid.$parent;
  let $grid = option.$grid;
  let originOption = $grid.params.originOption;
  if (option.type === "confirm" || option.type === "reset") {
    let tableName = originOption.tableName;
    if (option.type === "reset") {
      const { collectColumn } = $grid.getTableColumn();

      // 还原列的位置
      let oldColumns = originOption.columns || [];
      if (oldColumns.length > 0) {
        const restoredColumns = restoreColumnPosition(collectColumn);
        console.log("restoredColumns", restoredColumns);
        $grid.loadColumn(restoredColumns);
      } else {
        $grid.loadColumn(collectColumn);
      }
    }
    if (tableName) {
      setTimeout(() => {
        addTableJson(that, $grid, tableName);
      }, 200);
    }

    if (option && option.$event && option.$event.preventDefault) {
      option.$event.preventDefault(); // 取消事件的默认行为
    }
  }
  originOption.customCallback && originOption.customCallback(option);
}

function changeSelectCount(checked) {
  let checkedLength = checked.records.length;
}

function getTableData(that, tableRef, type, success) {
  if (
    configUtil.tableConfig.disableTableName ||
    settingConfig.tableStorageDisabled
  )
    return false;
  let $grid = getGrid(that, tableRef);
  let tableName = $grid.tableName;
  let url = USER_PREFIX + "/table_column/getTableData";
  let param = {
    tableName: tableName,
    type: type,
  };
  let data = null;
  return that.$http({
    async: false,
    url: url,
    method: "post",
    data: param,
    success: success,
  });
}

function addTableData(that, tableRef, value, success) {
  if (
    configUtil.tableConfig.disableTableName ||
    settingConfig.tableStorageDisabled
  )
    return false;
  let $grid = getGrid(that, tableRef);
  let tableName = $grid.tableName;
  if (tableName) {
    that.$http({
      method: "post",
      url: USER_PREFIX + "/table_column/addTableData",
      data: {
        tableName: tableName,
        type: "isQueryAllPage",
        data: value,
        success: success,
      },
    });
  }
}

function checkQueryTotal(that, tableRef, value) {
  let $grid = getGrid(that, tableRef);
  $grid.isQueryAllPage = value;
  let tableName = $grid.tableName;
  let option = $grid.getProxyInfo();
  let pagerConfig = $grid.pagerConfig;

  $grid.pagerConfig.layouts = pagerConfig.layouts || [];
  addTableData(that, tableRef, value);
  $grid.commitProxy("query");
}

function getPagerConfigLayouts(opts) {
  if (opts.showPageSizes !== false) {
    return ["Sizes", "PrevPage", "JumpNumber", "NextPage"];
  } else {
    return ["PrevPage", "JumpNumber", "NextPage"];
  }
}

modules = {
  initVxeTable,
  columnDrop,
  initOption,
  getTableJson,
  addTableJson,
  onColumnWitchChange,
  customHandle,
  changeSelectCount,
  getTableData,
  addTableData,
  checkQueryTotal,
  getCellValue,
  createParams,
};

if (!configUtil.Vue.prototype.$vxeTableUtil)
  configUtil.Vue.prototype.$vxeTableUtil = modules;

export default modules;
