<template>
  <div style="padding:1vh;">
    <div v-show="getTreeData.length > 0">
      <div class="search-container">
        <div class="search-wrapper">
          <q-input
            v-model="searchText"
            clearable
            class="search-input"
            label="搜索（支持两字以上的名字搜索）"
            placeholder="输入搜索并选择"
            @input="onSearchInput"
            @focus="showSearchMenu = true"
            @blur="hideSearchMenu"
          >
            <template v-slot:prepend>
              <q-icon name="search" class="search-icon" />
            </template>
            <template v-slot:append>
              <q-btn
                flat
                dense
                round
                icon="search"
                class="search-btn"
                @click="manualSearch"
              />
            </template>
          </q-input>

          <!-- 搜索菜单 -->
          <div
            v-show="showSearchMenu"
            class="search-menu"
          >
            <div class="search-results" v-if="searchOptions.length > 0">
              <div
                v-for="option in searchOptions"
                :key="option.key"
                class="search-result-item"
                @click="selectSearchOption(option)"
              >
                <div class="search-result-avatar">
                  <q-icon
                    :name="option.type === 'department' ? 'business' : 'person'"
                    :color="option.type === 'department' ? 'primary' : 'positive'"
                    size="sm"
                  />
                </div>
                <div class="search-result-content">
                  <div class="search-result-label">
                    {{ option.label }}
                  </div>
                  <div class="search-result-caption">
                    {{ option.type === 'department' ? '部门' : '人员' }}
                    <span v-if="option.key < 1000000 && option.key" class="search-result-id">
                      ID: {{ option.key }}
                    </span>
                  </div>
                </div>
                <div class="search-result-side">
                  <q-icon name="chevron_right" size="sm" color="grey-5" />
                </div>
              </div>
            </div>

            <!-- 无搜索结果 -->
            <div v-else-if="searchText && searchText.length > 0" class="no-results">
              <div class="no-result-item">
                <div class="no-result-avatar">
                  <q-icon name="info" color="grey-5" size="sm" />
                </div>
                <div class="no-result-content">
                  <div class="no-results-text">
                    没有找到匹配的人员或部门
                  </div>
                  <div class="no-results-hint">
                    请尝试其他关键词
                  </div>
                </div>
              </div>
            </div>
          </div>
        </div>
      </div>
      <div style="padding-top: 6vh">
        <Tree
          v-if="getTreeData.length > 0"
          ref="tree"
          checkable
          :checkedKeys="checkedKeys"
          @expand="onExpand"
          :expandedKeys="expandedKeys"
          :autoExpandParent="autoExpandParent"
          :treeData="getTreeData"
          :defaultExpandedKeys="defaultExpandedKeys"
          @check="onCheck"
          @select="onSelect"
        >

          <template slot="title" slot-scope="node">
              <span style="color: rgb(33, 186, 69);" v-if="checkedKeys.indexOf(node.key)>-1" >√</span>
              <span v-if="node.title.indexOf(searchValue) > -1">
                {{node.title.substr(0, node.title.indexOf(searchValue))}}
                <span style="color: #f50">{{searchValue }}</span>
                {{node.title.substr(node.title.indexOf(searchValue) + searchValue.length) }}
                <span style="color: #64b5fe">{{ node.no ? node.no:'' }}</span>
              </span>
              <span v-else>
                {{ node.title }}
                <span style="color: #64b5fe;">{{ node.no  ? node.no:'' }}</span>
              </span>
          </template>
        </Tree>
      </div>
    </div>
    <div v-show="!getTreeData.length > 0">
      正在加载组织机构组件...
    </div>
  </div>
</template>

<script>
  import Tree from 'ant-design-vue/lib/tree';
  import 'ant-design-vue/dist/antd.css';
  import AInputSearch from "ant-design-vue/es/input/Search";
  import {deptall} from "@/service/user/user";

  const dataList = []
  const generateList = (data) => {
    for (let i = 0; i < data.length; i++) {//高首骊
      const node = data[i]
      // const key = node.key
      dataList.push({//key,
        title: node.title,
        key: node.key,
        no:node.no,
        avatar:node.avatar,
        id: node.id,
        label: node.label,
        pid: node.pid,
        scopedSlots: {title: 'title'}
      })
      if (node.children) {
        generateList(node.children, node.key)
      }
      node.scopedSlots = {title: 'title'}
    }
  }

  const getParentKey = (key, tree) => {
    let parentKey
    for (let i = 0; i < tree.length; i++) {
      const node = tree[i]
      if (node.children) {
        if (node.children.some(item => item.key === key)) {
          parentKey = node.key
        } else if (getParentKey(key, node.children)) {
          parentKey = getParentKey(key, node.children)
        }
      }
    }
    return parentKey
  }
  export default {
    components: {
      AInputSearch,
      Tree
    },
    name: "organization-ant",
    data() {
      return {
        treeData: [],
        searchValue: '',
        searchText: '',// 自定义
        expandedKeys: [1000001],
        defaultExpandedKeys: [1000001],
        autoExpandParent: true,
        // 复选模式下的选中key（包含部门和人员）
        checkedKeys: [],
        // 准备提交的选中的部门
        checkedDepartment: [],
        // 准备提交的选中的人类对象
        checkedPeople: [],
        // 节点缓存，用于快速查找
        nodeCache: null,
        // 搜索相关
        searchOptions: [],
        showSearchMenu: false
      };
    },
    props: {
      value: {
        type: Array
      }
    },
    computed: {
      getTreeData() {
        // this.initTree();
        // generateList(this.$store.state.orgTreeData)
        // console.log(this.treeData)
        if (this.treeData.length > 0) {
          console.log('计算属性，组织机构，ok');
          this.$emit('ok', 'ok')
        }
        return  this.treeData;
      },
      getselectKeysStr(){
        return this.checkedKeys.map(item=>item).join(",")
      }
    },
    created() {
      this.initTree();
    },
    mounted() {
    },
    methods: {
      // 初始化树
      async initTree(){
        let Res = await deptall();
        let resdata = Res.data.data;
        this.treeData.push(resdata)
        generateList(this.treeData);

        // 构建节点缓存
        this.nodeCache = new Map();
        this.buildNodeCache(this.treeData);
      },
      onExpand(expandedKeys) {
        // console.log('onExpand', expandedKeys)
        // if not set autoExpandParent to false, if children expanded, parent can not collapse.
        // or, you can remove all expanded children keys.
        this.expandedKeys = expandedKeys
        this.autoExpandParent = false
      },
      onCheck(checkedKeys, e) {
        console.log('onCheck', checkedKeys, e);

        let finalCheckedKeys = [...checkedKeys];

        // 当勾选父节点时，自动勾选所有叶子节点
        if (e.checked && e.node.children && e.node.children.length > 0) {
          const leafKeys = this.getAllLeafKeys(e.node.children);
          finalCheckedKeys = [...new Set([...finalCheckedKeys, ...leafKeys])];
        }

        // 当取消勾选父节点时，取消勾选所有叶子节点
        if (!e.checked && e.node.children && e.node.children.length > 0) {
          const leafKeys = this.getAllLeafKeys(e.node.children);
          finalCheckedKeys = finalCheckedKeys.filter(key => !leafKeys.includes(key));
        }

        // 只在最终结果不同时才更新，避免不必要的触发
        if (JSON.stringify(finalCheckedKeys) !== JSON.stringify(this.checkedKeys)) {
          this.checkedKeys = finalCheckedKeys;
          // 更新选中的人员列表
          this.updateSelectedStaff();
        }
      },
      onSelect(selectedKeys, info) {
        // 在复选模式下，onSelect 可以用来处理一些辅助功能，比如展开/折叠
        // console.log('onSelect', selectedKeys, info);
      },


      // 搜索输入处理
      onSearchInput(value) {
        this.searchValue = value || '';

        if (value && value.length > 0) {
          // 过滤搜索选项
          this.searchOptions = dataList
            .filter(item => item.title == value || item.no == value)
            .map(item => ({
              key: item.key,
              label: item.title,
              displayLabel: `${item.title}${item.no ? ' (' + item.no + ')' : ''}${item.key >= 1000000 ? ' [部门]' : ' [人员]'}`,
              type: item.key >= 1000000 ? 'department' : 'person'
            }))
            .slice(0, 10); // 限制最多显示10个结果

          this.showSearchMenu = true;
        } else {
          this.searchOptions = [];
          this.showSearchMenu = false;
        }
      },

      // 手动搜索
      manualSearch() {
        if (this.searchText && this.searchText.length > 0) {
          this.onSearchInput(this.searchText);
        }
      },

      // 隐藏搜索菜单
      hideSearchMenu() {
        // 延迟隐藏，以便点击选项时能正常触发
        setTimeout(() => {
          this.showSearchMenu = false;
        }, 500);
      },

      // 选择搜索选项
      selectSearchOption(option) {
        console.log(option,'selectSearchOption=======')
        // 勾选选中的节点
        if (!this.checkedKeys.includes(option.key)) {
          this.checkedKeys = [...this.checkedKeys, option.key];
          this.updateSelectedStaff();
        }

        // 展开到选中节点的路径
        const parentKeys = this.getParentKeys(option.key, this.treeData);
        this.expandedKeys = [...new Set([...this.expandedKeys, ...parentKeys])];
        this.autoExpandParent = false;

        // 清空搜索状态
        this.searchText = '';
        this.searchOptions = [];
        this.showSearchMenu = false;
      },

      // 获取节点到根节点的路径
      getParentKeys(key, treeData, parents = []) {
        for (let node of treeData) {
          if (node.key === key) {
            return parents;
          }
          if (node.children) {
            const found = this.getParentKeys(key, node.children, [...parents, node.key]);
            if (found.length > parents.length) {
              return found;
            }
          }
        }
        return parents;
      },
      // 原有的搜索方法，现在主要用于高亮显示
      onChange(value) {
        if (!value) {
          this.searchValue = '';
          return;
        }

        this.searchValue = value;

        // 展开包含搜索结果的节点
        const expandedKeys = dataList.map((item) => {
          if (item.title.indexOf(value) > -1) {
            return getParentKey(item.key, this.getTreeData)
          }
          return null
        }).filter((item, i, self) => item && self.indexOf(item) === i)

        if (expandedKeys.length > 0) {
          this.expandedKeys = [...new Set([...this.expandedKeys, ...expandedKeys])];
          this.autoExpandParent = true;
        }
      },
      // 获取节点下的所有叶子节点key
      getAllLeafKeys(nodes) {
        let leafKeys = [];
        nodes.forEach(node => {
          if (node.children && node.children.length > 0) {
            // 如果有子节点，递归获取
            leafKeys = leafKeys.concat(this.getAllLeafKeys(node.children));
          } else {
            // 如果是叶子节点（人员），添加到结果中
            if (node.key < 1000000) { // 小于1000000的是人员
              leafKeys.push(node.key);
            }
          }
        });
        return leafKeys;
      },

      // 更新选中的人员列表
      updateSelectedStaff() {
        this.checkedPeople = [];
        this.checkedDepartment = [];

        // 使用 Map 缓存节点查找结果，避免重复遍历
        if (!this.nodeCache) {
          this.nodeCache = new Map();
          this.buildNodeCache(this.treeData);
        }

        // 遍历所有选中的key，区分人员和部门
        this.checkedKeys.forEach(key => {
          const node = this.nodeCache.get(key);
          if (node) {
            if (key < 1000000) { // 人员
              this.checkedPeople.push(node);
            } else { // 部门
              this.checkedDepartment.push(node);
            }
          }
        });

        // 向父组件发送选中的人员列表
        this.$emit('staffNode', this.checkedPeople);
      },

      // 构建节点缓存，避免每次查找都遍历树
      buildNodeCache(nodes) {
        nodes.forEach(node => {
          this.nodeCache.set(node.key, node);
          if (node.children && node.children.length > 0) {
            this.buildNodeCache(node.children);
          }
        });
      },


      orderStaffNode(){
        //对选择的人根据选择顺序排序
        let staffNode = []
        for(var i=0;i<this.checkedKeys.length;i++){
          let key = this.checkedKeys[i]
          if(key<1000000){//小于百万的为人员。大于为机构
            let node =this.checkedPeople.filter(item =>item.key==key)[0]
            if(node){
              staffNode.push(node);
            }
          }
        }
        return staffNode
      }
    },
    watch: {
      checkedKeys: {
        handler(val) {
          // 当 checkedKeys 改变时，同步更新 value，但避免循环
          const filteredKeys = val.filter(key => key < 1000000); // 只传递人员key给父组件

          // 只有当过滤后的key与当前value不同时才emit，避免循环
          if (JSON.stringify(filteredKeys) !== JSON.stringify(this.value || [])) {
            this.$emit('input', filteredKeys);
          }
        },
        deep: true
      },
      value: {
        handler(newValue) {
          // 只有当树已经加载完成且新值与当前checkedKeys中的人员key不同时才更新，避免循环
          if (this.treeData.length > 0) {
            const currentStaffKeys = this.checkedKeys.filter(key => key < 1000000);
            if (JSON.stringify(newValue || []) !== JSON.stringify(currentStaffKeys)) {
              this.checkedKeys = newValue || [];
              if (this.checkedKeys.length > 0) {
                this.updateSelectedStaff();
              }
            }
          }
        },
        immediate: true
      }
    },
  }

  // 筛选方法 结束
</script>

<style scoped>
.search-container {
  position: fixed;
  width: 17vw;
  z-index: 9999;
  padding: 1vh;
}

.search-wrapper {
  position: relative;
}

.search-input {
  padding-top: 10px;
  padding-left: 5px;
  border-radius: 4px !important;
  background: linear-gradient(135deg, #f8f9fa 0%, #ffffff 100%);
  /* box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08); */
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
}

.search-input:hover {
  box-shadow: 0 6px 20px rgba(0, 0, 0, 0.12);
  transform: translateY(-1px);
}

.search-input:focus-within {
  box-shadow: 0 8px 25px rgba(33, 150, 243, 0.15);
  transform: translateY(-2px);
}

.search-input >>> .q-field__control {
  border-radius: 12px;
  padding: 8px 16px;
}

.search-input >>> .q-field__label {
  font-weight: 500;
  color: #666;
  font-size: 12px;
}

.search-input >>> .q-field__native {
  font-size: 14px;
  font-weight: 400;
  padding-left: 12px !important;
  padding-top: 2px !important;
  padding-bottom: 2px !important;
}

.search-input >>> .q-field__native::placeholder {
  font-size: 14px;
  color: #999;
  position: relative;
  left: 0px;
  top: 0px;
  transform: none;
}

.search-icon {
  color: #999;
  transition: color 0.3s ease;
}

.search-input:hover .search-icon {
  color: #1976d2;
}

.search-btn {
  margin-right: 4px;
  transition: all 0.3s ease;
}

.search-btn:hover {
  background-color: rgba(25, 118, 210, 0.1);
  transform: scale(1.05);
}

.search-menu {
  border-radius: 12px;
  box-shadow: 0 8px 32px rgba(0, 0, 0, 0.12);
  border: 1px solid rgba(255, 255, 255, 0.2);
  backdrop-filter: blur(8px);
  background: rgba(255, 255, 255, 0.95);
  min-width: 16vw;
  max-width: 16vw;
  max-height: 300px;
  overflow-y: auto;
  position: absolute;
  top: 100%;
  left: 0;
  right: 0;
  z-index: 1000;
  margin-top: 8px;
}

.search-results {
  padding: 8px 0;
}

.search-result-item {
  display: flex;
  align-items: center;
  padding: 12px 16px;
  border-radius: 8px;
  margin: 2px 8px;
  cursor: pointer;
  transition: all 0.2s ease;
  border: 1px solid transparent;
}

.search-result-item:hover {
  background-color: rgba(25, 118, 210, 0.08);
  transform: translateX(2px);
  border-color: rgba(25, 118, 210, 0.1);
}

.search-result-avatar {
  flex-shrink: 0;
  width: 40px;
  height: 40px;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 50%;
  background-color: rgba(0, 0, 0, 0.04);
  margin-right: 12px;
}

.search-result-content {
  flex: 1;
  min-width: 0;
}

.search-result-side {
  flex-shrink: 0;
  margin-left: 8px;
  opacity: 0.6;
}

.search-result-label {
  font-weight: 500;
  color: #333;
  font-size: 14px;
}

.search-result-caption {
  font-size: 12px;
  color: #666;
  display: flex;
  align-items: center;
  gap: 8px;
}

.search-result-id {
  background-color: rgba(102, 102, 102, 0.1);
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 11px;
  font-weight: 500;
}

.no-results {
  padding: 16px;
  text-align: center;
}

.no-result-item {
  display: flex;
  align-items: center;
  padding: 12px 16px;
  justify-content: center;
}

.no-result-avatar {
  flex-shrink: 0;
  width: 40px;
  height: 40px;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 50%;
  background-color: rgba(0, 0, 0, 0.04);
  margin-right: 12px;
}

.no-result-content {
  flex: 1;
  text-align: left;
}

.no-results-text {
  color: #666;
  font-weight: 500;
  font-size: 14px;
}

.no-results-hint {
  color: #999;
  font-size: 12px;
  margin-top: 4px;
}

/* 滚动条美化 */
.search-menu::-webkit-scrollbar {
  width: 6px;
}

.search-menu::-webkit-scrollbar-track {
  background: rgba(0, 0, 0, 0.05);
  border-radius: 3px;
}

.search-menu::-webkit-scrollbar-thumb {
  background: rgba(0, 0, 0, 0.2);
  border-radius: 3px;
}

.search-menu::-webkit-scrollbar-thumb:hover {
  background: rgba(0, 0, 0, 0.3);
}

/* 响应式设计 */
@media (max-width: 768px) {
  .search-container {
    width: 90vw;
  }

  .search-menu {
    min-width: 90vw;
    max-width: 90vw;
  }
}
</style>
