UNPKG

@cimpress/react-components

Version:
73 lines 3.92 kB
var __rest = (this && this.__rest) || function (s, e) { var t = {}; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0) t[p] = s[p]; if (s != null && typeof Object.getOwnPropertySymbols === "function") for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) { if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) t[p[i]] = s[p[i]]; } return t; }; import React, { useState, useEffect } from 'react'; import { css, cx } from '@emotion/css'; import TabGroup from './TabGroup'; import Tab from './Tab'; import cvar from '../theme/cvar'; const generateTabMap = (tabs) => tabs.reduce((tabAcc, tab) => (Object.assign(Object.assign({}, tabAcc), { [tab.id]: tab })), {}); const validateIcons = (tabs) => { const tabsWithIcons = tabs.filter((tab) => Boolean(tab.icon)); const isValid = !tabsWithIcons.length || tabsWithIcons.length === tabs.length; if (!isValid) { console.warn('TabMenu: All tabs must have icons for them to render. Ignoring icons for all tabs...'); } return isValid; }; const validateDescriptions = (tabs) => { const tabsWithDescriptions = tabs.filter((tab) => Boolean(tab.description)); const isValid = !tabsWithDescriptions.length || tabsWithDescriptions.length === tabs.length; if (!isValid) { console.warn('TabMenu: All tabs must have descriptions for them to render. Ignoring descriptions for all tabs...'); } return isValid; }; const tabMenuStyle = css ` display: flex; `; const tabsBaseStyle = css ` display: flex; flex-direction: column; min-width: 250px; `; const activeTabBodyStyle = css ` padding-left: ${cvar('spacing-24')}; flex-grow: 3; `; export const TabMenu = (_a) => { var { className = '', activeTabId, tabs, tabGroups = [], onTabClick = () => { }, bodyStyle = {}, tabStyle = {}, style = {}, alwaysShowTabGroups = false } = _a, rest = __rest(_a, ["className", "activeTabId", "tabs", "tabGroups", "onTabClick", "bodyStyle", "tabStyle", "style", "alwaysShowTabGroups"]); const [tabMap, setTabMap] = useState(generateTabMap(tabs)); const [showIcons, setShowIcons] = useState(validateIcons(tabs)); const [showDescriptions, setShowDescriptions] = useState(validateDescriptions(tabs)); useEffect(() => { // Create a lookup mapping of tabs by id to optimize setTabMap(generateTabMap(tabs)); setShowIcons(validateIcons(tabs)); setShowDescriptions(validateDescriptions(tabs)); }, [tabs]); if (!tabs || !tabs.length) { return null; } let activeTab = tabs[0]; if (activeTabId) { activeTab = tabMap[activeTabId] || activeTab; } return (React.createElement("div", Object.assign({ className: cx('crc-tab-menu', tabMenuStyle, className), style: style }, rest), React.createElement("div", { className: tabsBaseStyle, style: tabStyle }, tabGroups.length > 1 || alwaysShowTabGroups ? tabGroups.map(({ label, tabIds = [] }) => (React.createElement(TabGroup, { key: `${label}-${tabIds.join('-')}`, label: label }, tabIds.map(tabId => { const { id, title, description, icon } = tabMap[tabId]; return (React.createElement(Tab, Object.assign({ key: id, id: id, title: title, onTabClick: onTabClick, isActive: activeTab.id === id }, (showIcons ? { icon } : {}), (showDescriptions ? { description } : {})))); })))) : tabs.map(({ id, title, description, icon }) => (React.createElement(Tab, Object.assign({ key: id, id: id, title: title, onTabClick: onTabClick, isActive: activeTab.id === id }, (showIcons ? { icon } : {}), (showDescriptions ? { description } : {})))))), React.createElement("div", { className: activeTabBodyStyle, style: bodyStyle }, activeTab && activeTab.body))); }; //# sourceMappingURL=TabMenu.js.map