@carbon/ibm-products
Version:
Carbon for IBM Products
134 lines (132 loc) • 4.37 kB
JavaScript
/**
* Copyright IBM Corp. 2020, 2026
*
* This source code is licensed under the Apache-2.0 license found in the
* LICENSE file in the root directory of this source tree.
*/
import { __toESM } from "../../_virtual/_rolldown/runtime.js";
import { require_classnames } from "../../node_modules/classnames/index.js";
import { pkg } from "../../settings.js";
import { getDevtoolsProps } from "../../global/js/utils/devtools.js";
import NavItem_default, { blockClass as blockClass$1 } from "./NavItem.js";
import NavList_default, { blockClass as blockClass$2 } from "./NavList.js";
import React, { useEffect, useRef, useState } from "react";
import PropTypes from "prop-types";
//#region src/components/Nav/Nav.jsx
/**
* Copyright IBM Corp. 2024, 2024
*
* This source code is licensed under the Apache-2.0 license found in the
* LICENSE file in the root directory of this source tree.
*/
var import_classnames = /* @__PURE__ */ __toESM(require_classnames());
const componentName = "Nav";
const blockClass = `${pkg.prefix}--nav`;
/**
* @deprecated This component is deprecated
*/
let Nav = React.forwardRef(({ activeHref, className, children, heading, label, ...rest }, ref) => {
const [_activeHref, setActiveHref] = useState(activeHref);
const navigationLists = useRef({});
useEffect(() => {
if (!_activeHref && window.location) {
const { hash, pathname } = window.location;
setActiveHref(pathname + hash);
}
}, [_activeHref]);
/**
* Creates a new child list item.
* @param {NavItem} child The child list item to create.
* @param {number} index The index of the child list item.
* @returns {NavItem} The new child list item.
*/
const buildNewItemChild = (child, index) => {
const key = `${blockClass$1}--${index}`;
return /* @__PURE__ */ React.createElement(NavItem_default, {
...child.props,
activeHref: _activeHref,
key,
onClick: (event, href) => handleItemClick(event, href, child.props.onClick)
});
};
/**
* Creates a new child list.
* @param {NavList} child The child list to create.
* @param {number} index The index of the child list.
* @returns {NavList} The new child list.
*/
const buildNewListChild = (child, index) => {
const key = `${blockClass$2}--${index}`;
return /* @__PURE__ */ React.createElement(NavList_default, {
...child.props,
activeHref: _activeHref,
id: key,
key,
onListClick: handleListClick,
onItemClick: handleItemClick,
ref: (el) => navigationLists.current[key] = el
});
};
/**
* Handles toggling the list item.
* @param {SyntheticEvent} event The event fired when the list item is toggled.
* @param {string} href The URL of the list item.
*/
const handleItemClick = (event, href, onClick) => {
event.stopPropagation();
const { type, which } = event;
if ((which === 13 || which === 32 || type === "click") && href !== _activeHref) setActiveHref(href);
if (onClick) onClick(event);
};
/**
* Handles when a list has been selected.
* @param {number} id The index of the list.
*/
const handleListClick = (id) => {
Object.keys(navigationLists.current).forEach((key) => {
if (key !== id && !navigationLists.current[key].isExpandedOnPageLoad) navigationLists.current[key].close();
});
};
return /* @__PURE__ */ React.createElement("nav", {
className: (0, import_classnames.default)(blockClass, className),
"aria-label": label,
ref,
...getDevtoolsProps(componentName),
...rest
}, heading && /* @__PURE__ */ React.createElement("h1", { className: `${blockClass}__heading` }, heading), /* @__PURE__ */ React.createElement("ul", {
className: `${blockClass}__wrapper`,
role: "menubar"
}, React.Children.map(children, (child, index) => {
return child?.type?.displayName === NavList_default.displayName ? buildNewListChild(child, index) : buildNewItemChild(child, index);
})));
});
Nav.deprecated = {
level: "warn",
details: `This component is deprecated`
};
Nav.propTypes = {
/**
* Hypertext reference for active page.
*/
activeHref: PropTypes.string,
/**
* Child elements.
*/
children: PropTypes.node,
/**
* Extra classes to add.
*/
className: PropTypes.string,
/**
* Heading.
*/
heading: PropTypes.string,
/**
* Aria-label on the rendered `nav` element.
*/
label: PropTypes.string.isRequired
};
Nav = pkg.checkComponentEnabled(Nav, componentName);
Nav.displayName = componentName;
//#endregion
export { Nav };