"use strict";
Object.defineProperties(exports, { __esModule: { value: true }, [Symbol.toStringTag]: { value: "Module" } });
const types = require("../../../../utils/types.js");
const shared_esmBundler = require("../../../../../../@vue/shared/dist/shared.esm-bundler.js");
const util = require("./util.js");
const node = require("./node.js");
const Vue = require("vue");
const isNil = require("../../../../../../lodash-es/isNil.js");
var TreeStore = class {
  constructor(options) {
    this.lazy = false;
    this.checkStrictly = false;
    this.autoExpandParent = false;
    this.defaultExpandAll = false;
    this.checkDescendants = false;
    this.currentNode = null;
    this.currentNodeKey = null;
    for (const option in options) if (shared_esmBundler.hasOwn(options, option)) this[option] = options[option];
    this.nodesMap = {};
  }
  initialize() {
    this.root = new node.default({
      data: this.data,
      store: this
    });
    this.root.initialize();
    if (this.lazy && this.load) {
      const loadFn = this.load;
      loadFn(this.root, (data) => {
        this.root.doCreateChildren(data);
        this._initDefaultCheckedNodes();
      }, shared_esmBundler.NOOP);
    } else this._initDefaultCheckedNodes();
  }
  filter(value) {
    const filterNodeMethod = this.filterNodeMethod;
    const lazy = this.lazy;
    const traverse = async function(node2) {
      const childNodes = node2.root ? node2.root.childNodes : node2.childNodes;
      for (const [index, child] of childNodes.entries()) {
        child.visible = !!(filterNodeMethod == null ? void 0 : filterNodeMethod.call(child, value, child.data, child));
        if (index % 80 === 0 && index > 0) await Vue.nextTick();
        await traverse(child);
      }
      if (!node2.visible && childNodes.length) {
        let allHidden = true;
        allHidden = !childNodes.some((child) => child.visible);
        if (node2.root) node2.root.visible = allHidden === false;
        else node2.visible = allHidden === false;
      }
      if (!value) return;
      if (node2.visible && !node2.isLeaf) {
        if (!lazy || node2.loaded) node2.expand();
      }
    };
    traverse(this);
  }
  setData(newVal) {
    if (newVal !== this.root.data) {
      this.nodesMap = {};
      this.root.setData(newVal);
      this._initDefaultCheckedNodes();
      this.setCurrentNodeKey(this.currentNodeKey);
    } else this.root.updateChildren();
  }
  getNode(data) {
    if (data instanceof node.default) return data;
    const key = shared_esmBundler.isObject(data) ? util.getNodeKey(this.key, data) : data;
    return this.nodesMap[key] || null;
  }
  insertBefore(data, refData) {
    var _a;
    const refNode = this.getNode(refData);
    (_a = refNode.parent) == null ? void 0 : _a.insertBefore({ data }, refNode);
  }
  insertAfter(data, refData) {
    var _a;
    const refNode = this.getNode(refData);
    (_a = refNode.parent) == null ? void 0 : _a.insertAfter({ data }, refNode);
  }
  remove(data) {
    const node2 = this.getNode(data);
    if (node2 && node2.parent) {
      if (node2 === this.currentNode) this.currentNode = null;
      node2.parent.removeChild(node2);
    }
  }
  append(data, parentData) {
    const parentNode = !types.isPropAbsent(parentData) ? this.getNode(parentData) : this.root;
    if (parentNode) parentNode.insertChild({ data });
  }
  _initDefaultCheckedNodes() {
    const defaultCheckedKeys = this.defaultCheckedKeys || [];
    const nodesMap = this.nodesMap;
    defaultCheckedKeys.forEach((checkedKey) => {
      const node2 = nodesMap[checkedKey];
      if (node2) node2.setChecked(true, !this.checkStrictly);
    });
  }
  _initDefaultCheckedNode(node2) {
    const defaultCheckedKeys = this.defaultCheckedKeys || [];
    if (!isNil.default(node2.key) && defaultCheckedKeys.includes(node2.key)) node2.setChecked(true, !this.checkStrictly);
  }
  setDefaultCheckedKey(newVal) {
    if (newVal !== this.defaultCheckedKeys) {
      this.defaultCheckedKeys = newVal;
      this._initDefaultCheckedNodes();
    }
  }
  registerNode(node2) {
    const key = this.key;
    if (!node2 || !node2.data) return;
    if (!key) this.nodesMap[node2.id] = node2;
    else {
      const nodeKey = node2.key;
      if (!isNil.default(nodeKey)) this.nodesMap[nodeKey] = node2;
    }
  }
  deregisterNode(node2) {
    if (!this.key || !node2 || !node2.data) return;
    node2.childNodes.forEach((child) => {
      this.deregisterNode(child);
    });
    delete this.nodesMap[node2.key];
  }
  getCheckedNodes(leafOnly = false, includeHalfChecked = false) {
    const checkedNodes = [];
    const traverse = function(node2) {
      (node2.root ? node2.root.childNodes : node2.childNodes).forEach((child) => {
        if ((child.checked || includeHalfChecked && child.indeterminate) && (!leafOnly || leafOnly && child.isLeaf)) checkedNodes.push(child.data);
        traverse(child);
      });
    };
    traverse(this);
    return checkedNodes;
  }
  getCheckedKeys(leafOnly = false) {
    return this.getCheckedNodes(leafOnly).map((data) => (data || {})[this.key]);
  }
  getHalfCheckedNodes() {
    const nodes = [];
    const traverse = function(node2) {
      (node2.root ? node2.root.childNodes : node2.childNodes).forEach((child) => {
        if (child.indeterminate) nodes.push(child.data);
        traverse(child);
      });
    };
    traverse(this);
    return nodes;
  }
  getHalfCheckedKeys() {
    return this.getHalfCheckedNodes().map((data) => (data || {})[this.key]);
  }
  _getAllNodes() {
    const allNodes = [];
    const nodesMap = this.nodesMap;
    for (const nodeKey in nodesMap) if (shared_esmBundler.hasOwn(nodesMap, nodeKey)) allNodes.push(nodesMap[nodeKey]);
    return allNodes;
  }
  updateChildren(key, data) {
    const node2 = this.nodesMap[key];
    if (!node2) return;
    const childNodes = node2.childNodes;
    for (let i = childNodes.length - 1; i >= 0; i--) {
      const child = childNodes[i];
      this.remove(child.data);
    }
    for (let i = 0, j = data.length; i < j; i++) {
      const child = data[i];
      this.append(child, node2.data);
    }
  }
  _setCheckedKeys(key, leafOnly = false, checkedKeys) {
    const allNodes = this._getAllNodes().sort((a, b) => a.level - b.level);
    const cache = /* @__PURE__ */ Object.create(null);
    const keys = Object.keys(checkedKeys);
    allNodes.forEach((node2) => node2.setChecked(false, false));
    const cacheCheckedChild = (node2) => {
      node2.childNodes.forEach((child) => {
        var _a;
        cache[child.data[key]] = true;
        if ((_a = child.childNodes) == null ? void 0 : _a.length) cacheCheckedChild(child);
      });
    };
    for (let i = 0, j = allNodes.length; i < j; i++) {
      const node2 = allNodes[i];
      const nodeKey = node2.data[key].toString();
      if (!keys.includes(nodeKey)) {
        if (node2.checked && !cache[nodeKey]) node2.setChecked(false, false);
        continue;
      }
      if (node2.childNodes.length) cacheCheckedChild(node2);
      if (node2.isLeaf || this.checkStrictly) {
        node2.setChecked(true, false);
        continue;
      }
      node2.setChecked(true, true);
      if (leafOnly) {
        node2.setChecked(false, false, true);
        const traverse = function(node3) {
          node3.childNodes.forEach((child) => {
            if (!child.isLeaf) child.setChecked(false, false, true);
            traverse(child);
          });
          node3.reInitChecked();
        };
        traverse(node2);
      }
    }
  }
  setCheckedNodes(array, leafOnly = false) {
    const key = this.key;
    const checkedKeys = {};
    array.forEach((item) => {
      checkedKeys[(item || {})[key]] = true;
    });
    this._setCheckedKeys(key, leafOnly, checkedKeys);
  }
  setCheckedKeys(keys, leafOnly = false) {
    this.defaultCheckedKeys = keys;
    const key = this.key;
    const checkedKeys = {};
    keys.forEach((key2) => {
      checkedKeys[key2] = true;
    });
    this._setCheckedKeys(key, leafOnly, checkedKeys);
  }
  setDefaultExpandedKeys(keys) {
    keys = keys || [];
    this.defaultExpandedKeys = keys;
    keys.forEach((key) => {
      const node2 = this.getNode(key);
      if (node2) node2.expand(null, this.autoExpandParent);
    });
  }
  setChecked(data, checked, deep) {
    const node2 = this.getNode(data);
    if (node2) node2.setChecked(!!checked, deep);
  }
  getCurrentNode() {
    return this.currentNode;
  }
  setCurrentNode(currentNode) {
    const prevCurrentNode = this.currentNode;
    if (prevCurrentNode) prevCurrentNode.isCurrent = false;
    this.currentNode = currentNode;
    this.currentNode.isCurrent = true;
  }
  setUserCurrentNode(node2, shouldAutoExpandParent = true) {
    var _a;
    const key = node2[this.key];
    const currNode = this.nodesMap[key];
    this.setCurrentNode(currNode);
    if (shouldAutoExpandParent && this.currentNode && this.currentNode.level > 1) (_a = this.currentNode.parent) == null ? void 0 : _a.expand(null, true);
  }
  setCurrentNodeKey(key, shouldAutoExpandParent = true) {
    var _a;
    this.currentNodeKey = key;
    if (types.isPropAbsent(key)) {
      this.currentNode && (this.currentNode.isCurrent = false);
      this.currentNode = null;
      return;
    }
    const node2 = this.getNode(key);
    if (node2) {
      this.setCurrentNode(node2);
      if (shouldAutoExpandParent && this.currentNode && this.currentNode.level > 1) (_a = this.currentNode.parent) == null ? void 0 : _a.expand(null, true);
    }
  }
};
exports.default = TreeStore;
