<!--
图件的图层树

add by RYG
-->
<template>
  <div class="tree-component">
    <!-- 加载状态（由父组件控制） -->
    <!-- <div v-if="loading" class="loading">
      加载中……
    </div> -->
    <div class="tree-container">
      <div class="operation" v-if="!props.isPopup">
        <el-button v-for="(btn, index) in iconButtons" :key="index" class="square-icon-button"
          :icon="getNodeIcon(btn.id)" :type="btn.type" :title="btn.title" text @click="() => setLayerStatus(btn.id)" />
        <el-divider direction="vertical" />
        <el-button class="square-icon-button" :icon="Delete" type="danger" circle title="删除" text
          @click="deleteLayer" />
      </div>
      <!-- 树形结构（使用外部传入的数据） -->
      <el-tree ref="treeRef" v-model="selectedKeys" :data="treeData" show-checkbox node-key="id" default-expand-all
        :highlight-current="true" :props="defaultProps" placeholder="点击展开加载子节点..." clearable @check="handleCheck"
        class="custom-tree">
        <template #default="{ node, data }">
          <div class="tree-node">
            <span class="icon-container">
              <!-- <el-icon :size="treeConfig.iconSize" :class="'icon-orange'">
                <component :is="data.icon" />
              </el-icon> -->
              <el-icon v-if="data.status" :size="treeConfig.iconSize" :class="'icon-orange'">
                <component :is="getNodeIcon(data.status)" />
              </el-icon>
            </span>
            <span>{{ node.label }}</span>
            <!-- <span v-if="data.count" class="node-count">{{ data.count }}</span> -->
          </div>
        </template>
      </el-tree>
      <div class="popup-operation" v-if="props.isPopup && props.showOper">
        <el-button :icon="Finished" @click="handleConfirm" type="primary">确定</el-button>
      </div>
    </div>
    <!-- 操作按钮 -->
    <!-- <div class="actions" v-if="treeData.length">
      <el-button type="primary" @click="getSelectedNodes">获取选中项</el-button>
      <el-button @click="clearSelection">清空选择</el-button>
    </div> -->
    <LoadingDialog v-model="loading" ref="loadingRef" :timeout="3000" message="正在加载图层……" @timeout="onTimeout" />
  </div>
</template>

<script setup>
import { ref, onMounted } from "vue";
import { emitter } from "@/utils/eventBus";
import { ElTree, ElButton } from "element-plus";
import { Hide, Lock, Edit, Delete, Finished } from "@element-plus/icons-vue";
import { useRoute } from 'vue-router';
import { COMMAND, EMIT_COMMAND } from '~/utils/commandTypes'
import { useWebSocket } from '@/composables/useWebSocket'
// 消息提示（自动隐藏）
const { $toastMessage } = useNuxtApp();

const route = useRoute();

const { messages, onMessage, status, send } = useWebSocket();

const props = defineProps({
  isPopup: { type: Boolean, default: false },
  showOper: { type: Boolean, defalut: true },
  tokenKey: { type: String, default: 'drawerToken' }
  // containerHeight: { type: Number, default: window.innerHeight - 75 }
});

// const currentTabTokenKey = computed(() => props.tokenKey);

const currentToken = ref('');

const isPopup = computed(() => {
  return props.isPopup;
});


const iconButtons = [
  { icon: "edit", title: "可编辑", type: "warning", id: 1 },
  { icon: "lock", title: "只读", type: "warning", id: 2 },
  { icon: "hide", title: "隐藏", type: "warning", id: 3 },
  // { icon: Delete, title: "删除", type: "danger" },
];

// 树配置
const treeConfig = ref({
  fontSize: 13,
  iconSize: 13,
  nodeHeight: 25,
  currentHighlight: true,
  showIcons: true,
});

// 树的数据
const treeData = ref([]);
// 加载状态
const loading = ref(false);
const loadingRef = ref(null);
// 得到的原始图层数据
const sourceData = ref([]);
// 响应式数据
const treeRef = ref(null);
// 选中的节点 ID 数组
const selectedKeys = ref([]);

// 定义选择节点事件
const emit = defineEmits(['selectedChanged']);

// 树形配置（节点唯一标识、标签、子节点字段）
const defaultProps = {
  children: "children",
  label: "label",
};

const unsubscribe = onMessage((data) => {
  try {
    if (!data) return; // 如果没有新消息，直接返回
    const json = JSON.parse(data);
    const evtType = json.type;
    switch (evtType) {
      case COMMAND.RELOAD_LAYER:
        let layerData = json.data;
        showLayers(layerData);
        loadingRef.value.close();
        break;
    }
  } finally {
  }
})

const onTimeout = () => {
  $toastMessage.error("加载图层超时，请稍后重试！");
};

// 组装树的数据
const showLayers = (layerData) => {
  if (!layerData) {
    return;
  }
  // 确保layerData是有效的JSON字符串
  if (typeof layerData === "string") {
    layerData = JSON.parse(layerData);
  }

  // 确保转换后是数组
  if (!Array.isArray(layerData)) {
    console.error("Invalid layer data format - expected array");
    return;
  }

  sourceData.value = layerData; // 假设data是树形结构数据
  // 创建图层根节点
  let layerNodes = [
    {
      id: "Layer:",
      pId: "-1",
      label: "图层",
      open: true,
      halfCheck: false,
      status: 1,
      icon: getNodeIcon(1), // 默认图标为可编辑
      children: [],
    },
  ];

  layerNodes[0].children = layerData.map((node) => processNode(node));

  treeData.value = layerNodes;
};

const setLayerStatus = (status) => {
  let nodes = getSelectedNodes();
  nodes = nodes.filter((node) => node.name !== "图层");
  let nCount = nodes.length;
  if (nCount === 0) {
    return;
  }
  let strStatus = "10";
  if (status === 2) {
    strStatus = "11";
  } else if (status === 3) {
    strStatus = "12";
  }
  let statusData = "";
  for (let i = 0; i < nCount; i++) {
    // var imgUrl = iconButtons.value[status].icon;
    // nodes[i].status = status;
    // treeObj.updateNode(nodes[i]);
    editNodeById(treeData.value, nodes[i].id, status);
    statusData += strStatus + "|Layer:\\" + nodes[i].fullPath + "\r\n";
  }
  send(COMMAND.SET_LAYER_STATUS, { layerData: statusData }, getToken());
  // 处理图层状态设置逻辑
};

const deleteLayer = () => {
  let nodes = getSelectedNodes();
  nodes = nodes.filter((node) => node.name !== "图层");
  let nCount = nodes.length;
  if (nCount === 0) {
    return;
  }
  let statusData = "";
  for (let i = 0; i < nCount; i++) {
    // statusData += (nodes[i].id + ",");
    statusData += "Layer:\\" + nodes[i].fullPath + ",";
    // treeRef.value.removeNode(nodes[i]);
    removeNodeById(treeData.value, nodes[i].id);
  }
  send(COMMAND.DELETE_LAYER, { layers: statusData, widthChild: 1 }, getToken());
};

// 删除指定ID的节点
const removeNodeById = (tree, id) => {
  for (let i = 0; i < tree.length; i++) {
    if (tree[i].id === id) {
      const removedNode = tree.splice(i, 1)[0];
      return { removed: true, removedNode };
    }

    if (tree[i].children && tree[i].children.length > 0) {
      const result = removeNodeById(tree[i].children, id);
      if (result.removed) {
        return result;
      }
    }
  }
  return { removed: false };
};

// 修改节点的状态
const editNodeById = (tree, id, status) => {
  for (let i = 0; i < tree.length; i++) {
    if (tree[i].id === id) {
      // 在这里可以修改节点的属性
      tree[i].status = status;
      tree[i].icon = getNodeIcon(status); // 更新图标
      return true; // 找到并修改节点，返回true
    }

    if (tree[i].children && tree[i].children.length > 0) {
      const found = editNodeById(tree[i].children, id, status);
      if (found) {
        return true; // 如果在子节点中找到并修改，返回true
      }
    }
  }
  return false; // 没有找到节点，返回false
};

// 获取当前图件的token
const getToken = () => {
  currentToken.value = localStorage.getItem(props.tokenKey);
  return currentToken.value || '';
}

onMounted(() => {

  getToken();
  clearTree();
  // send("GetLayers", null, currentToken.value);
  loading.value = true;

  sourceChanged();
  getLayer();
  emitter.on(EMIT_COMMAND.SOURCE_CHANGED, sourceChanged);
  emitter.on(EMIT_COMMAND.REFRESH_LAYER, getLayer);
});

const sourceChanged = () => {
  clearTree();
}

const getLayer = () => {
  send(COMMAND.GET_LAYERS, null, getToken(), currentToken.value);
}

const getNodeIcon = (status) => {
  switch (status) {
    case 1:
      return Edit;
    case 2:
      return Lock;
    case 3:
      return Hide;
    default:
      return Edit; // 默认图标
  }
};

// 递归处理节点和子节点
const processNode = (node) => {
  let nodeIcon = getNodeIcon(node.status);

  const treeNode = {
    id: node.id,
    pId: "Layer:", // node.ParentId.toString(),
    label: node.name || "",
    open: false,
    icon: nodeIcon,
    status: node.status || 0,
    fullPath: node.fullPath || "",
    children: [],
  };

  // 如果有子节点，递归处理
  if (node.children && node.children.length > 0) {
    treeNode.children = node.children.map((child) => {
      const childNode = processNode(child);
      // 确保子节点的pId指向父节点id
      childNode.pId = treeNode.id;
      return childNode;
    });
    // 有子节点时默认展开
    treeNode.open = true;
  }
  return treeNode;
};

onBeforeUnmount(() => {
  // emitter.off("ReloadLayer");
  clearTree();
  unsubscribe();
  emitter.off(EMIT_COMMAND.SOURCE_CHANGED);
  emitter.off(EMIT_COMMAND.REFRESH_LAYER)
});

const clearTree = () => {
  treeData.value = null;
}

// 选中节点事件处理
const handleCheck = (currentNode, checkStatus) => {
  selectedKeys.value = checkStatus.checkedKeys;
  if (props.isPopup && !props.showOper) {

    let statusData = getSelectedLayers();
    emit(EMIT_COMMAND.SELECTED_CHANGED, statusData);
  }
};

// 获取选中的节点
const getSelectedNodes = () => {
  // 通过 Tree 实例获取选中节点的完整数据
  const selectedNodes = treeRef.value?.getCheckedNodes() || [];
  return selectedNodes;
};

// 清空选择
const clearSelection = () => {
  treeRef.value?.setCheckedKeys([]);
  selectedKeys.value = [];
};

// 确定选择按钮事件
const handleConfirm = () => {
  let statusData = getSelectedLayers();
  if (statusData === '') {
    return;
  }
  emitter.emit(EMIT_COMMAND.SELECTED_LAYER, statusData);
  // 得到数据之后清空选择
  clearSelection();
};

// 获取选中的图层
const getSelectedLayers = () => {
  let nodes = getSelectedNodes();
  nodes = nodes.filter((node) => node.name !== "图层");
  let nCount = nodes.length;
  if (nCount === 0) {
    return '';
  }
  let statusData = "";
  for (let i = 0; i < nCount; i++) {
    statusData += nodes[i].fullPath + ",";
  }

  return statusData;
};

onUnmounted(() => {
  unsubscribe();
});
</script>

<style scoped>
.tree-component {
  width: 100%;
  height: 100%;
  margin: 0 auto;
  padding: 0;
  border: 0;
  background: #fff;
  max-width: 240px;
}

.tree-container {
  width: 100%;
  /* height: calc(100vh - 75px); */
  height: 100%;
  overflow: auto;
  /* background: lightblue; */
  padding: 0;
  vertical-align: middle;
  /* background: #2c3e50; */
}

.operation {
  height: 40px;
  vertical-align: middle;
  padding-top: 5px;
  padding-left: 10px;
  border: 1px solid #eaeaea;
}

.popup-operation {
  height: 50px;
  vertical-align: middle;
  padding-top: 10px;
  padding-right: 10px;
  padding-bottom: 10px;
  border-top: 1px solid #eaeaea;
  display: flex;
  flex-direction: row;
  justify-content: flex-end;
}

.square-icon-button {
  width: 25px;
  height: 25px;
  padding: 0 !important;
  /* 去掉内边距 */
  border-radius: 4px;
  /* 设置圆角为4px，若要直角则设为0 */
  display: inline-flex;
  justify-content: center;
  align-items: center;
}

.square-icon-button:hover {
  color: #ec0a0a;
  /* 鼠标悬停时的背景色 */
}

.loading {
  width: 100%;
  height: 100%;
  display: flex;
  background: #333;
  vertical-align: middle;
  justify-content: center;
  padding: 0;
  font-size: 14px;
  color: #3498db;
}

.actions {
  margin-top: 15px;
  display: flex;
  gap: 5px;
}

.custom-tree {
  /* 自定义文字大小 */
  --tree-font-size: 13px;
  --tree-icon-size: 13px;
  /* overflow: auto; */

  font-size: var(--tree-font-size);
}

.custom-tree .el-tree-node__content {
  height: 25px !important;
  transition: background-color 0.2s;
  padding: 0;
  border-radius: 6px;
}

.custom-tree .el-tree-node__content:hover {
  background-color: rgba(52, 152, 219, 0.1);
}

.custom-tree .el-tree-node__label {
  /* font-weight: 300; */
  color: #2c3e50;
  white-space: nowrap;
  margin-left: 0;
}

.custom-tree .el-tree-node__expand-icon {
  font-size: var(--tree-icon-size);
  transition: transform 0.3s;
}

.custom-tree .el-tree-node__expand-icon.expanded {
  transform: rotate(90deg);
}

.custom-tree .el-tree-node.is-current>.el-tree-node__content {
  background-color: rgba(52, 152, 219, 0.15);
}

.custom-tree .el-tree-node.is-current>.el-tree-node__content .el-tree-node__label {
  color: #2980b9;
  /* font-weight: 400; */
}

.icon-container {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  margin-right: 2px;
  width: 16px;
  height: 16px;
}

.icon-blue {
  color: #3498db;
}

.icon-green {
  color: #27ae60;
}

.icon-orange {
  color: #e67e22;
}

.icon-purple {
  color: #9b59b6;
}

.el-tree {
  --el-tree-node-hover-bg-color: rgba(52, 152, 219, 0.1);
  --el-tree-text-color: #2c3e50;
  --el-tree-expand-icon-color: #e4d61b;
  /* background: #333; */
  display: flex;
}
</style>
