"use strict";

var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
exports.__esModule = true;
exports.VerticalMovementDirection = void 0;
exports.addToTree = addToTree;
exports.getDepth = exports.generateUniqueGroupId = void 0;
exports.getDropParent = getDropParent;
exports.getNodeAtPosition = getNodeAtPosition;
exports.getNodePosition = getNodePosition;
exports.getSiblingsByNodePosition = getSiblingsByNodePosition;
exports.getValuesByKey = void 0;
exports.hoverAboveItself = hoverAboveItself;
exports.isFistItem = isFistItem;
exports.isItemHasChildren = isItemHasChildren;
exports.isLastItem = isLastItem;
exports.isRootItem = isRootItem;
exports.moveItem = moveItem;
exports.moveItemOutsideOfTheParent = moveItemOutsideOfTheParent;
exports.moveItemToTheChildOfPrevSibling = moveItemToTheChildOfPrevSibling;
exports.moveItemVertically = moveItemVertically;
exports.recursiveMap = recursiveMap;
exports.removeFromTree = removeFromTree;
exports.setCollapse = setCollapse;
exports.swapItems = swapItems;
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { (0, _defineProperty2.default)(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
var VerticalMovementDirection = exports.VerticalMovementDirection = {
  top: -1,
  bottom: 1
};
var generateUniqueGroupId = () => {
  if (process.env.NODE_ENV === 'test') {
    return 'test_id';
  }
  return Symbol('nestable-list-base-id');
};
exports.generateUniqueGroupId = generateUniqueGroupId;
var getDepth = (item, childrenProperty) => {
  // returns depth of item and children
  var depth = 0;
  if (item[childrenProperty]) {
    item[childrenProperty].forEach(d => {
      var tmpDepth = getDepth(d, childrenProperty);
      if (tmpDepth > depth) {
        depth = tmpDepth;
      }
    });
  }
  return depth + 1;
};
exports.getDepth = getDepth;
var getValuesByKey = (data, key, childrenProp) => {
  var values = [data[key]];
  if (data[childrenProp]) {
    data[childrenProp].forEach(item => {
      values.push(...getValuesByKey(item, key, childrenProp));
    });
  }
  return values;
};
exports.getValuesByKey = getValuesByKey;
var arrayRemove = (items, index) => {
  return [...items.slice(0, index), ...items.slice(index + 1)];
};
var arrayAdd = (items, index, item) => {
  return [...items.slice(0, index), item, ...items.slice(index)];
};
function removeFromTree(items, position, childrenProperty) {
  if (position.length === 0) {
    return items;
  }
  var [currentIndex, ...restPosition] = position;
  if (restPosition.length === 0) {
    return arrayRemove(items, currentIndex);
  }

  // Recursively process nested items
  return items.map((item, index) => {
    if (index === currentIndex) {
      var _item$childrenPropert;
      return _objectSpread(_objectSpread({}, item), {}, {
        [childrenProperty]: removeFromTree((_item$childrenPropert = item[childrenProperty]) !== null && _item$childrenPropert !== void 0 ? _item$childrenPropert : [], restPosition, childrenProperty)
      });
    }
    return item;
  });
}
function addToTree(items, item, position, childrenProperty) {
  if (position.length === 0) {
    return items;
  }
  var [currentIndex, ...restPosition] = position;
  if (restPosition.length === 0) {
    return arrayAdd(items, currentIndex, item);
  }

  // Recursively process nested items
  return items.map((currentItem, index) => {
    if (index === currentIndex) {
      var _currentItem$children;
      return _objectSpread(_objectSpread({}, currentItem), {}, {
        [childrenProperty]: addToTree((_currentItem$children = currentItem[childrenProperty]) !== null && _currentItem$children !== void 0 ? _currentItem$children : [], item, restPosition, childrenProperty)
      });
    }
    return currentItem;
  });
}
function swapItems(items, firstItem, secondItem) {
  var childProp = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : 'children';
  return recursiveMap(items, item => {
    if (item.id === firstItem.id) {
      return secondItem;
    }
    if (item.id === secondItem.id) {
      return firstItem;
    }
    return item;
  }, childProp);
}
function getSiblingsByNodePosition(items) {
  var position = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
  var childProp = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'children';
  return position.reduce((siblings, pos, i) => {
    if (siblings && siblings[pos]) {
      if (position.length - 1 === i) {
        return siblings;
      }
      return siblings[pos][childProp];
    }
    return null;
  }, items);
}
function getNodeAtPosition(items) {
  var position = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
  var childProp = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'children';
  return position.reduce((siblings, pos, i) => {
    if (siblings[pos]) {
      if (position.length - 1 === i) {
        return siblings[pos];
      }
      return siblings[pos][childProp];
    }
    return null;
  }, items);
}
function getNodePosition(items, item) {
  var childProp = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'children';
  var position = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : [];
  if (!items) {
    return;
  }
  for (var i = 0; i < items.length; i++) {
    var currentPosition = [...position, i];
    if (item.id === items[i].id) {
      return currentPosition;
    }
    var nodePosition = getNodePosition(items[i][childProp], item, childProp, currentPosition);
    if (nodePosition) {
      return nodePosition;
    }
  }
}
function recursiveMap(items, predicateFn) {
  var childProp = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'children';
  return items.map(currentItem => {
    var item = predicateFn(currentItem);
    if (item !== currentItem) {
      return item;
    }
    if (currentItem[childProp]) {
      return _objectSpread(_objectSpread({}, currentItem), {}, {
        children: recursiveMap(currentItem[childProp], predicateFn)
      });
    }
    return currentItem;
  });
}
function isLastItem(siblings, item) {
  return siblings && siblings[siblings.length - 1] === item;
}
function isFistItem(siblings, item) {
  return siblings && siblings[0] === item;
}
function isRootItem(depth) {
  return depth === 1;
}
function hoverAboveItself(prevPosition, nextPosition) {
  return prevPosition.every((position, index) => {
    return nextPosition[index] === position;
  });
}
function isItemHasChildren(item, childrenProperty) {
  return Boolean(item[childrenProperty] && item[childrenProperty].length);
}
function getDropParent(items, nextPosition, childrenProperty) {
  return nextPosition.slice(1, nextPosition.length - 1).reduce((item, childIndex) => {
    if (!item) {
      return null;
    }
    return item[childrenProperty][childIndex];
  }, items[nextPosition[0]]);
}
function moveItem(items, item, currentPosition, newPosition) {
  var childrenProp = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : 'children';
  items = removeFromTree(items, currentPosition, childrenProp);
  return addToTree(items, item, newPosition, childrenProp);
}
function moveItemToTheChildOfPrevSibling(items, item) {
  var childrenProp = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'children';
  var currentPosition = getNodePosition(items, item, childrenProp);
  // if there is not prev sibling we cannot move
  if (currentPosition[currentPosition.length - 1] === 0) {
    return items;
  }
  var newPosition = currentPosition.reduce((acc, pos, index, arr) => {
    if (index === arr.length - 1) {
      acc.push(pos - 1);
      acc.push(0);
    } else {
      acc.push(pos);
    }
    return acc;
  }, []);
  return moveItem(items, item, currentPosition, newPosition);
}
function getVerticalMovedPosition(items, position, step) {
  var childProp = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : 'children';
  var suitableNextParent = [...position].reverse().reduce((acc, pos, index) => {
    if (acc) {
      return acc;
    }
    var prefix = position.slice(0, position.length - 1 - index);
    var siblings = getSiblingsByNodePosition(items, position.slice(0, position.length - index), childProp);
    for (var i = pos + step; i >= 0 && i < siblings.length; i += step) {
      var candidate = [...prefix, i];
      var candidateSiblings = getSiblingsByNodePosition(items, candidate, childProp);
      if (!candidateSiblings) {
        return null;
      }
      var totalDepth = getDepth(getNodeAtPosition(items, candidate, childProp), childProp) + position.length - index;
      if (totalDepth >= position.length) {
        return candidate;
      }
    }
    return acc;
  }, null);
  if (!suitableNextParent) {
    return null;
  }
  if (position.length === suitableNextParent.length) {
    return suitableNextParent;
  }
  return position.reduce((acc, _, index) => {
    var lastItem = index === position.length - 1;
    if (suitableNextParent[index] !== undefined) {
      acc.push(suitableNextParent[index]);
    } else {
      var siblings = getSiblingsByNodePosition(items, [...acc, 0], childProp);
      if (!siblings) {
        acc.push(0);
        return acc;
      }
      var maxIndex = lastItem ? siblings.length : siblings.length - 1;
      var candidateIndex = step < 0 ? maxIndex : 0;
      while (candidateIndex >= 0 && candidateIndex <= maxIndex) {
        var candidate = [...acc, candidateIndex];
        if (lastItem) {
          return candidate;
        }
        var candidateDepth = getDepth(getNodeAtPosition(items, candidate, childProp), childProp) + index;
        if (candidateDepth < position.length - 1) {
          candidateIndex += step;
          continue;
        }
        return candidate;
      }
    }
    return acc;
  }, []);
}
function getParentPosition(position) {
  return position.slice(0, position.length - 1);
}
function moveItemVertically(_ref) {
  var {
    items,
    item,
    step = VerticalMovementDirection.bottom,
    childProp = 'children',
    preventChangeParent = false,
    enforcePinnedOrder = false
  } = _ref;
  var currentPosition = getNodePosition(items, item, childProp);
  var newPosition = getVerticalMovedPosition(items, currentPosition, step, childProp);
  if (!newPosition) {
    return items;
  }
  if (preventChangeParent) {
    var prevParentPath = currentPosition.slice(0, -1);
    var nextParentPath = newPosition.slice(0, -1);
    var prevParent = getDropParent(items, prevParentPath, childProp);
    var nextParent = getDropParent(items, nextParentPath, childProp);
    if ((prevParent == null ? void 0 : prevParent.id) !== (nextParent == null ? void 0 : nextParent.id)) {
      return items;
    }
  }
  if (enforcePinnedOrder) {
    var siblings = getSiblingsByNodePosition(items, newPosition, childProp);
    var targetItem = siblings == null ? void 0 : siblings[newPosition[newPosition.length - 1]];
    var shouldProhibitPinMoveDown = !!item.isPinned && !targetItem.isPinned;
    var shouldProhibitNonPinMoveUp = !item.isPinned && !!targetItem.isPinned;
    if (shouldProhibitPinMoveDown || shouldProhibitNonPinMoveUp) {
      return items;
    }
  }
  return moveItem(items, item, currentPosition, newPosition, childProp);
}
function moveItemOutsideOfTheParent(items, item) {
  var childProp = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'children';
  var currentPosition = getNodePosition(items, item, childProp);
  // if currentPosition is root of the tree we cannot move item to the left
  if (currentPosition.length < 2) {
    return items;
  }
  var newPosition = getParentPosition(currentPosition);
  newPosition[newPosition.length - 1] = newPosition[newPosition.length - 1] + 1;
  return moveItem(items, item, currentPosition, newPosition);
}
function setCollapse(items, itemId, isCollapsed) {
  return recursiveMap(items, item => {
    if (itemId === item.id) {
      return _objectSpread(_objectSpread({}, item), {}, {
        isCollapsed
      });
    }
    return item;
  });
}
//# sourceMappingURL=utils.js.map