/**
 * ldesign v0.2.3
 * (c) 2022年9月24日 swimly
 * @license MIT
 */

'use strict';

Object.defineProperty(exports, '__esModule', { value: true });

var Vue = require('vue');
var raf = require('raf');
var isString = require('lodash/isString');
var utils_easing = require('./easing.js');

function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; }

var Vue__default = /*#__PURE__*/_interopDefaultLegacy(Vue);
var raf__default = /*#__PURE__*/_interopDefaultLegacy(raf);
var isString__default = /*#__PURE__*/_interopDefaultLegacy(isString);

const isServer = Vue__default["default"].prototype.$isServer || typeof window === "undefined";
const trim = str => (str || "").replace(/^[\s\uFEFF]+|[\s\uFEFF]+$/g, "");
const on = (() => {
  if (!isServer && document.addEventListener) {
    return (element, event, handler, options) => {
      if (element && event && handler) {
        element.addEventListener(event, handler, options);
        return () => off(element, event, handler, options);
      }
    };
  }

  return (element, event, handler) => {
    if (element && event && handler) {
      element.attachEvent(`on${event}`, handler);
      return () => off(element, event, handler);
    }
  };
})();
const off = (() => {
  if (!isServer && document.removeEventListener) {
    return (element, event, handler, options) => {
      if (element && event) {
        element.removeEventListener(event, handler, options);
      }
    };
  }

  return (element, event, handler) => {
    if (element && event) {
      element.detachEvent(`on${event}`, handler);
    }
  };
})();
function once(element, event, handler, options) {
  const handlerFn = typeof handler === "function" ? handler : handler.handleEvent;

  const callback = evt => {
    handlerFn(evt);
    off(element, event, callback, options);
  };

  on(element, event, callback, options);
}
function hasClass(el, cls) {
  if (!el || !cls) return false;
  if (cls.indexOf(" ") !== -1) throw new Error("className should not contain space.");

  if (el.classList) {
    return el.classList.contains(cls);
  }

  return ` ${el.className} `.indexOf(` ${cls} `) > -1;
}
function addClass(el, cls) {
  if (!el) return;
  let curClass = el.className;
  const classes = (cls || "").split(" ");

  for (let i = 0, j = classes.length; i < j; i++) {
    const clsName = classes[i];
    if (!clsName) continue;

    if (el.classList) {
      el.classList.add(clsName);
    } else if (!hasClass(el, clsName)) {
      curClass += ` ${clsName}`;
    }
  }

  if (!el.classList) {
    el.className = curClass;
  }
}
function removeClass(el, cls) {
  if (!el || !cls) return;
  const classes = cls.split(" ");
  let curClass = ` ${el.className} `;

  for (let i = 0, j = classes.length; i < j; i++) {
    const clsName = classes[i];
    if (!clsName) continue;

    if (el.classList) {
      el.classList.remove(clsName);
    } else if (hasClass(el, clsName)) {
      curClass = curClass.replace(` ${clsName} `, " ");
    }
  }

  if (!el.classList) {
    el.className = trim(curClass);
  }
}
const getAttach = (node, triggerNode) => {
  const attachNode = typeof node === "function" ? node(triggerNode) : node;

  if (!attachNode) {
    return document.body;
  }

  if (isString__default["default"](attachNode)) {
    return document.querySelector(attachNode);
  }

  if (attachNode instanceof HTMLElement) {
    return attachNode;
  }

  return document.body;
};
const getScrollContainer = function () {
  let container = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : "body";

  if (isString__default["default"](container)) {
    return document.querySelector(container);
  }

  if (typeof container === "function") {
    return container();
  }

  return container;
};

function isWindow(obj) {
  return obj && obj === obj.window;
}

function getScroll(target, isLeft) {
  if (typeof window === "undefined" || !target) {
    return 0;
  }

  const method = isLeft ? "scrollLeft" : "scrollTop";
  let result = 0;

  if (isWindow(target)) {
    result = target[isLeft ? "pageXOffset" : "pageYOffset"];
  } else if (target instanceof Document) {
    result = target.documentElement[method];
  } else if (target) {
    result = target[method];
  }

  return result;
}
function scrollTo(target, opt) {
  const {
    container = window,
    duration = 450,
    easing = utils_easing.easeInOutCubic
  } = opt;
  const scrollTop = getScroll(container);
  const startTime = Date.now();
  return new Promise(res => {
    const fnc = () => {
      const timestamp = Date.now();
      const time = timestamp - startTime;
      const nextScrollTop = easing(Math.min(time, duration), scrollTop, target, duration);

      if (isWindow(container)) {
        container.scrollTo(window.pageXOffset, nextScrollTop);
      } else if (container instanceof HTMLDocument || container.constructor.name === "HTMLDocument") {
        container.documentElement.scrollTop = nextScrollTop;
      } else {
        container.scrollTop = nextScrollTop;
      }

      if (time < duration) {
        raf__default["default"](fnc);
      } else {
        raf__default["default"](res);
      }
    };

    raf__default["default"](fnc);
  });
}

function containerDom(parent, child) {
  if (parent && child) {
    let pNode = child;

    while (pNode) {
      if (parent === pNode) {
        return true;
      }

      const {
        parentNode
      } = pNode;
      pNode = parentNode;
    }
  }

  return false;
}

const clickOut = (els, cb) => {
  on(document, "click", event => {
    if (Array.isArray(els)) {
      const isFlag = Array.from(els).every(item => containerDom(item, event.target) === false);
      isFlag && cb && cb();
    } else {
      if (containerDom(els, event.target)) {
        return false;
      }

      cb && cb();
    }
  });
};
const isNodeOverflow = ele => {
  const {
    clientWidth = 0,
    scrollWidth = 0
  } = ele;
  return scrollWidth > clientWidth;
};
const removeDom = el => {
  if (el.remove) {
    el.remove();
  } else {
    el.parentNode.removeChild(el);
  }
};

exports.addClass = addClass;
exports.clickOut = clickOut;
exports.getAttach = getAttach;
exports.getScroll = getScroll;
exports.getScrollContainer = getScrollContainer;
exports.hasClass = hasClass;
exports.isNodeOverflow = isNodeOverflow;
exports.isServer = isServer;
exports.off = off;
exports.on = on;
exports.once = once;
exports.removeClass = removeClass;
exports.removeDom = removeDom;
exports.scrollTo = scrollTo;
exports.trim = trim;
//# sourceMappingURL=dom.js.map
