import * as React from 'react';
import PrimeReact from 'primereact/api';
import { useEventListener, useMountEffect, useUpdateEffect, useUnmountEffect } from 'primereact/hooks';
import { classNames, IconUtils, ObjectUtils, DomHandler, ZIndexUtils } from 'primereact/utils';
import { Ripple } from 'primereact/ripple';

function _extends() {
  _extends = Object.assign || function (target) {
    for (var i = 1; i < arguments.length; i++) {
      var source = arguments[i];

      for (var key in source) {
        if (Object.prototype.hasOwnProperty.call(source, key)) {
          target[key] = source[key];
        }
      }
    }

    return target;
  };

  return _extends.apply(this, arguments);
}

function _arrayWithHoles(arr) {
  if (Array.isArray(arr)) return arr;
}

function _iterableToArrayLimit(arr, i) {
  var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"];

  if (_i == null) return;
  var _arr = [];
  var _n = true;
  var _d = false;

  var _s, _e;

  try {
    for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) {
      _arr.push(_s.value);

      if (i && _arr.length === i) break;
    }
  } catch (err) {
    _d = true;
    _e = err;
  } finally {
    try {
      if (!_n && _i["return"] != null) _i["return"]();
    } finally {
      if (_d) throw _e;
    }
  }

  return _arr;
}

function _arrayLikeToArray(arr, len) {
  if (len == null || len > arr.length) len = arr.length;

  for (var i = 0, arr2 = new Array(len); i < len; i++) {
    arr2[i] = arr[i];
  }

  return arr2;
}

function _unsupportedIterableToArray(o, minLen) {
  if (!o) return;
  if (typeof o === "string") return _arrayLikeToArray(o, minLen);
  var n = Object.prototype.toString.call(o).slice(8, -1);
  if (n === "Object" && o.constructor) n = o.constructor.name;
  if (n === "Map" || n === "Set") return Array.from(o);
  if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen);
}

function _nonIterableRest() {
  throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
}

function _slicedToArray(arr, i) {
  return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest();
}

var MenubarSub = /*#__PURE__*/React.memo( /*#__PURE__*/React.forwardRef(function (props, ref) {
  var _React$useState = React.useState(null),
      _React$useState2 = _slicedToArray(_React$useState, 2),
      activeItemState = _React$useState2[0],
      setActiveItemState = _React$useState2[1];

  var _useEventListener = useEventListener({
    type: 'click',
    listener: function listener(event) {
      if (ref && ref.current && !ref.current.contains(event.target)) {
        setActiveItemState(null);
      }
    }
  }),
      _useEventListener2 = _slicedToArray(_useEventListener, 1),
      bindDocumentClickListener = _useEventListener2[0];

  var onItemMouseEnter = function onItemMouseEnter(event, item) {
    if (item.disabled || props.mobileActive) {
      event.preventDefault();
      return;
    }

    if (props.root) {
      if (activeItemState || props.popup) {
        setActiveItemState(item);
      }
    } else {
      setActiveItemState(item);
    }
  };

  var onItemClick = function onItemClick(event, item) {
    if (item.disabled) {
      event.preventDefault();
      return;
    }

    if (!item.url) {
      event.preventDefault();
    }

    if (item.command) {
      item.command({
        originalEvent: event,
        item: item
      });
    }

    if (item.items) activeItemState && item === activeItemState ? setActiveItemState(null) : setActiveItemState(item);else onLeafClick();
  };

  var onItemKeyDown = function onItemKeyDown(event, item) {
    var listItem = event.currentTarget.parentElement;

    switch (event.which) {
      //down
      case 40:
        if (props.root) item.items && expandSubmenu(item, listItem);else navigateToNextItem(listItem);
        event.preventDefault();
        break;
      //up

      case 38:
        !props.root && navigateToPrevItem(listItem);
        event.preventDefault();
        break;
      //right

      case 39:
        if (props.root) {
          var nextItem = findNextItem(listItem);
          nextItem && nextItem.children[0].focus();
        } else {
          item.items && expandSubmenu(item, listItem);
        }

        event.preventDefault();
        break;
      //left

      case 37:
        props.root && navigateToPrevItem(listItem);
        event.preventDefault();
        break;
    }

    props.onKeyDown && props.onKeyDown(event, listItem);
  };

  var onChildItemKeyDown = function onChildItemKeyDown(event, childListItem) {
    if (props.root) {
      //up
      if (event.which === 38 && childListItem.previousElementSibling == null) {
        collapseMenu(childListItem);
      }
    } else {
      //left
      if (event.which === 37) {
        collapseMenu(childListItem);
      }
    }
  };

  var expandSubmenu = function expandSubmenu(item, listItem) {
    setActiveItemState(item);
    setTimeout(function () {
      listItem.children[1].children[0].children[0].focus();
    }, 50);
  };

  var collapseMenu = function collapseMenu(listItem) {
    setActiveItemState(null);
    listItem.parentElement.previousElementSibling.focus();
  };

  var navigateToNextItem = function navigateToNextItem(listItem) {
    var nextItem = findNextItem(listItem);
    nextItem && nextItem.children[0].focus();
  };

  var navigateToPrevItem = function navigateToPrevItem(listItem) {
    var prevItem = findPrevItem(listItem);
    prevItem && prevItem.children[0].focus();
  };

  var findNextItem = function findNextItem(item) {
    var nextItem = item.nextElementSibling;
    return nextItem ? DomHandler.hasClass(nextItem, 'p-disabled') || !DomHandler.hasClass(nextItem, 'p-menuitem') ? findNextItem(nextItem) : nextItem : null;
  };

  var findPrevItem = function findPrevItem(item) {
    var prevItem = item.previousElementSibling;
    return prevItem ? DomHandler.hasClass(prevItem, 'p-disabled') || !DomHandler.hasClass(prevItem, 'p-menuitem') ? findPrevItem(prevItem) : prevItem : null;
  };

  var onLeafClick = function onLeafClick() {
    setActiveItemState(null);
    props.onLeafClick && props.onLeafClick();
  };

  useMountEffect(function () {
    bindDocumentClickListener();
  });
  useUpdateEffect(function () {
    !props.parentActive && setActiveItemState(null);
  }, [props.parentActive]);

  var createSeparator = function createSeparator(index) {
    var key = 'separator_' + index;
    return /*#__PURE__*/React.createElement("li", {
      key: key,
      className: "p-menu-separator",
      role: "separator"
    });
  };

  var createSubmenu = function createSubmenu(item) {
    if (item.items) {
      return /*#__PURE__*/React.createElement(MenubarSub, {
        menuProps: props.menuProps,
        model: item.items,
        mobileActive: props.mobileActive,
        onLeafClick: onLeafClick,
        onKeyDown: onChildItemKeyDown,
        parentActive: item === activeItemState
      });
    }

    return null;
  };

  var createMenuitem = function createMenuitem(item, index) {
    var key = item.label + '_' + index;
    var className = classNames('p-menuitem', {
      'p-menuitem-active': activeItemState === item
    }, item.className);
    var linkClassName = classNames('p-menuitem-link', {
      'p-disabled': item.disabled
    });
    var iconClassName = classNames('p-menuitem-icon', item.icon);
    var submenuIconClassName = classNames('p-submenu-icon pi', {
      'pi-angle-down': props.root,
      'pi-angle-right': !props.root
    });
    var icon = IconUtils.getJSXIcon(item.icon, {
      className: 'p-menuitem-icon'
    }, {
      props: props.menuProps
    });
    var label = item.label && /*#__PURE__*/React.createElement("span", {
      className: "p-menuitem-text"
    }, item.label);
    var submenuIcon = item.items && /*#__PURE__*/React.createElement("span", {
      className: submenuIconClassName
    });
    var submenu = createSubmenu(item);
    var content = /*#__PURE__*/React.createElement("a", {
      href: item.url || '#',
      role: "menuitem",
      className: linkClassName,
      target: item.target,
      "aria-haspopup": item.items != null,
      onClick: function onClick(event) {
        return onItemClick(event, item);
      },
      onKeyDown: function onKeyDown(event) {
        return onItemKeyDown(event, item);
      }
    }, icon, label, submenuIcon, /*#__PURE__*/React.createElement(Ripple, null));

    if (item.template) {
      var defaultContentOptions = {
        onClick: function onClick(event) {
          return onItemClick(event, item);
        },
        onKeyDown: function onKeyDown(event) {
          return onItemKeyDown(event, item);
        },
        className: linkClassName,
        labelClassName: 'p-menuitem-text',
        iconClassName: iconClassName,
        submenuIconClassName: submenuIconClassName,
        element: content,
        props: props
      };
      content = ObjectUtils.getJSXElement(item.template, item, defaultContentOptions);
    }

    return /*#__PURE__*/React.createElement("li", {
      key: key,
      role: "none",
      className: className,
      style: item.style,
      onMouseEnter: function onMouseEnter(event) {
        return onItemMouseEnter(event, item);
      }
    }, content, submenu);
  };

  var createItem = function createItem(item, index) {
    return item.separator ? createSeparator(index) : createMenuitem(item, index);
  };

  var createMenu = function createMenu() {
    return props.model ? props.model.map(createItem) : null;
  };

  var role = props.root ? 'menubar' : 'menu';
  var className = classNames({
    'p-submenu-list': !props.root,
    'p-menubar-root-list': props.root
  });
  var submenu = createMenu();
  return /*#__PURE__*/React.createElement("ul", {
    ref: ref,
    className: className,
    role: role
  }, submenu);
}));
MenubarSub.displayName = 'MenubarSub';

var Menubar = /*#__PURE__*/React.memo( /*#__PURE__*/React.forwardRef(function (props, ref) {
  var _React$useState = React.useState(false),
      _React$useState2 = _slicedToArray(_React$useState, 2),
      mobileActiveState = _React$useState2[0],
      setMobileActiveState = _React$useState2[1];

  var rootMenuRef = React.useRef(null);
  var menuButtonRef = React.useRef(null);

  var _useEventListener = useEventListener({
    type: 'click',
    listener: function listener(event) {
      if (mobileActiveState && isOutsideClicked(event)) {
        setMobileActiveState(false);
      }
    }
  }),
      _useEventListener2 = _slicedToArray(_useEventListener, 2),
      bindDocumentClickListener = _useEventListener2[0],
      unbindDocumentClickListener = _useEventListener2[1];

  var toggle = function toggle(event) {
    event.preventDefault();
    setMobileActiveState(function (prevMobileActive) {
      return !prevMobileActive;
    });
  };

  var onLeafClick = function onLeafClick() {
    setMobileActiveState(false);
  };

  var isOutsideClicked = function isOutsideClicked(event) {
    return rootMenuRef.current !== event.target && !rootMenuRef.current.contains(event.target) && menuButtonRef.current !== event.target && !menuButtonRef.current.contains(event.target);
  };

  useUpdateEffect(function () {
    if (mobileActiveState) {
      ZIndexUtils.set('menu', rootMenuRef.current, PrimeReact.autoZIndex, PrimeReact.zIndex['menu']);
      bindDocumentClickListener();
    } else {
      unbindDocumentClickListener();
      ZIndexUtils.clear(rootMenuRef.current);
    }
  }, [mobileActiveState]);
  useUnmountEffect(function () {
    ZIndexUtils.clear(rootMenuRef.current);
  });
  React.useImperativeHandle(ref, function () {
    return {
      toggle: toggle,
      useCustomContent: useCustomContent
    };
  });

  var createStartContent = function createStartContent() {
    if (props.start) {
      var _start = ObjectUtils.getJSXElement(props.start, props);

      return /*#__PURE__*/React.createElement("div", {
        className: "p-menubar-start"
      }, _start);
    }

    return null;
  };

  var createEndContent = function createEndContent() {
    if (props.end) {
      var _end = ObjectUtils.getJSXElement(props.end, props);

      return /*#__PURE__*/React.createElement("div", {
        className: "p-menubar-end"
      }, _end);
    }

    return null;
  };

  var createMenuButton = function createMenuButton() {
    /* eslint-disable */
    var button = /*#__PURE__*/React.createElement("a", {
      ref: menuButtonRef,
      href: '#',
      role: "button",
      tabIndex: 0,
      className: "p-menubar-button",
      onClick: toggle
    }, /*#__PURE__*/React.createElement("i", {
      className: "pi pi-bars"
    }));
    /* eslint-enable */

    return button;
  };

  var otherProps = ObjectUtils.findDiffKeys(props, Menubar.defaultProps);
  var className = classNames('p-menubar p-component', {
    'p-menubar-mobile-active': mobileActiveState
  }, props.className);
  var start = createStartContent();
  var end = createEndContent();
  var menuButton = createMenuButton();
  var submenu = /*#__PURE__*/React.createElement(MenubarSub, {
    ref: rootMenuRef,
    menuProps: props,
    model: props.model,
    root: true,
    mobileActive: mobileActiveState,
    onLeafClick: onLeafClick
  });
  return /*#__PURE__*/React.createElement("div", _extends({
    id: props.id,
    className: className,
    style: props.style
  }, otherProps), start, menuButton, submenu, end);
}));
Menubar.displayName = 'Menubar';
Menubar.defaultProps = {
  __TYPE: 'Menubar',
  id: null,
  model: null,
  style: null,
  className: null,
  start: null,
  end: null
};

export { Menubar };
