UNPKG

@zohodesk/dot

Version:

In this Library, we Provide Some Basic Components to Build Your Application

307 lines (296 loc) 10.3 kB
import React, { useState, useRef } from 'react'; import { useEffectCallOnlyAfterState } from '@zohodesk/hooks'; import { defaultProps } from "./props/defaultProps"; import { propTypes } from "./props/propTypes"; import { Icon } from '@zohodesk/icons'; import Popup from '@zohodesk/components/es/v1/Popup/Popup'; import { Box, Container } from '@zohodesk/components/es/v1/Layout'; import DropDownHeading from '@zohodesk/components/es/v1/DropDown/DropDownHeading'; import TextBoxIcon from '@zohodesk/components/es/v1/TextBoxIcon/TextBoxIcon'; import Loader from '@zohodesk/svg/lib/Loader/Loader'; import EmptySearch from '@zohodesk/svg/lib/emptystate/version3/EmptySearch'; import CommonEmptyState from "../../../emptystate/CommonEmptyState/CommonEmptyState"; import StatusListItem from "../StatusListItem/StatusListItem"; import commonStyle from '@zohodesk/components/es/common/common.module.css'; import ResponsiveDropBox from '@zohodesk/components/es/v1/ResponsiveDropBox/ResponsiveDropBox'; import { ResponsiveReceiver } from '@zohodesk/components/es/Responsive/CustomResponsive'; import { useUniqueId } from '@zohodesk/components/es/Provider/IdProvider'; import btnStyle from '@zohodesk/components/es/semantic/Button/semanticButton.module.css'; import style from "../../../../list/status/StatusDropdown/StatusDropdown.module.css"; function StatusDropdown(props) { let { value, removeClose, boxSize, keyName, idName, title, isSearch, isArrow, placeHolderText, className, right, left, top, bottom, isPopupOpen: isOpen, isPopupReady, position, getTargetRef, getContainerRef, dataId, searchBoxSize, searchEmptyHint, searchErrorText, activeStyle, showOnHover = false, isDisabled, showIconOnHover, isReadOnly, hoverStyle, isEditable, needTick, dataTitle, isDataLoaded, children, targetAlign, needResponsive, arrowIconPosition, statusColor, needExternalPopupState = false, isPopupActive = false, needMultiLineText, boxPosition, togglePopup, onTogglePopup, onClick, onSelectLabel, isFetchingOptions, getNextOptions, options, isAbsolutePositioningNeeded, isRestrictScroll, positionsOffset, targetOffset, renderTargetElement, renderFooterElement, a11y = {} } = props; const [optionsList, setOptionsList] = useState(options); const [searchString, setSearchString] = useState(''); const getAriaId = useUniqueId(); const { tabIndex = 0, ariaLabelledby, ariaLabel } = a11y; let isPopupOpen = needExternalPopupState ? isPopupActive && isOpen : isOpen; let containerClass = `${className ? className : ''} ${isPopupReady ? activeStyle ? activeStyle : '' : showIconOnHover ? style.hoverIcon : ''} ${isDisabled ? commonStyle.disabled : isReadOnly ? style.readOnly : !isEditable ? style.cursorDefault : !showOnHover ? `${style.cursor} ${hoverStyle ? hoverStyle : ''}` : `${hoverStyle ? hoverStyle : ''} ${style.cursorDefault}`}`; let ariaTitleId = getAriaId(); function emptySearchSVG() { return /*#__PURE__*/React.createElement(EmptySearch, { size: "small" }); } function handleTogglePopup(e) { !isPopupOpen && onSelectLabel && onSelectLabel(e); onTogglePopup && onTogglePopup(isPopupOpen); togglePopup(e, boxPosition); } function onSelect(element, e) { onClick && onClick(e, element); onTogglePopup && onTogglePopup(isPopupOpen); togglePopup(e); } function searchList(value) { let foptions = options.filter(dept => dept[keyName].toLowerCase().indexOf(value.toLowerCase()) != -1); return foptions; } function handleChange(value, e) { let foptions = searchList(value); setSearchString(value); setOptionsList(foptions); } function onSearchClear() { let foptions = searchList(''); setSearchString(''); setOptionsList(foptions); } function handleScroll(e) { if (e.target.scrollTop + e.target.offsetHeight > e.target.scrollHeight - 1) { getNextOptions && getNextOptions(e); } } function responsiveFunc(_ref) { let { mediaQueryOR } = _ref; return { tabletMode: mediaQueryOR([{ maxWidth: 700 }]) }; } useEffectCallOnlyAfterState(() => { setOptionsList(options); }, [options.length]); useEffectCallOnlyAfterState(() => { isPopupOpen && onSearchClear(); }, [isPopupOpen]); return /*#__PURE__*/React.createElement("div", { className: style.posRel, onMouseEnter: showOnHover && !isDisabled && !isReadOnly && isEditable ? handleTogglePopup : undefined, onMouseLeave: showOnHover && !isDisabled && !isReadOnly && isEditable ? handleTogglePopup : undefined }, renderTargetElement ? renderTargetElement({ handleTogglePopup, isPopupOpen, getTargetRef }) : /*#__PURE__*/React.createElement(Container, { tagName: "button", alignBox: "row", className: `${style.container} ${containerClass} ${btnStyle.buttonReset}`, onClick: !showOnHover && !isDisabled && !isReadOnly && isEditable ? handleTogglePopup : null, eleRef: getTargetRef, align: targetAlign, isCover: false, dataId: dataId, disabled: isDisabled || isReadOnly ? true : false, "aria-haspopup": isSearch ? 'listbox' : 'menu', "aria-expanded": isPopupReady && isEditable ? true : false, tabIndex: tabIndex, "aria-labelledby": ariaLabelledby, "aria-label": ariaLabel, "aria-disabled": isDisabled || isReadOnly }, children ? children : /*#__PURE__*/React.createElement(Box, { className: `${style.value} toggleDropText`, shrink: true, tagName: "span", "data-title": dataTitle, dataId: `${dataId}_value` }, value), isEditable ? /*#__PURE__*/React.createElement(Icon, { "aria-hidden": true, size: "7", name: "ZD-down", iconClass: `${'toggleDropIcon'} ${style.arrow} ${style[`${arrowIconPosition}_arrow`]}`, dataId: "statusdownarrow" }) : null), isPopupOpen && isEditable ? /*#__PURE__*/React.createElement(ResponsiveReceiver, { query: responsiveFunc, responsiveId: "Helmet" }, _ref2 => { let { tabletMode } = _ref2; return /*#__PURE__*/React.createElement(ResponsiveDropBox, { boxPosition: position, isActive: isPopupReady, onClick: removeClose, size: boxSize, right: right, left: left, top: top, bottom: bottom, isArrow: isArrow, isAnimate: true, getRef: getContainerRef, customClass: { customDropBoxWrap: style.dropBoxContainer }, needResponsive: needResponsive, isResponsivePadding: true, needFocusScope: true, onClose: handleTogglePopup, dataId: `${dataId}_dropbox`, isAbsolutePositioningNeeded: isAbsolutePositioningNeeded, isRestrictScroll: isRestrictScroll, positionsOffset: positionsOffset, targetOffset: targetOffset, customProps: { focusScopeProps: { searchValue: searchString, loadNextOptions: getNextOptions, isFetchingOptions: isFetchingOptions } } }, /*#__PURE__*/React.createElement(React.Fragment, null, isSearch ? /*#__PURE__*/React.createElement(Box, { className: style.search }, /*#__PURE__*/React.createElement(TextBoxIcon, { placeHolder: placeHolderText, onChange: handleChange, value: searchString, onClear: onSearchClear, size: searchBoxSize, customProps: { TextBoxProps: { 'data-a11y-autofocus': true } }, a11y: { ariaHaspopup: isSearch ? 'listbox' : 'menu', ariaExpanded: isPopupReady, role: 'combobox', ariaActivedescendant: isPopupReady ? value : '', ariaOwns: ariaTitleId }, dataId: `${dataId}_search` })) : null, title && optionsList.length != 0 && /*#__PURE__*/React.createElement(Box, { className: style.title }, /*#__PURE__*/React.createElement(DropDownHeading, { htmlId: ariaTitleId, text: title, a11y: { role: 'heading' } })), /*#__PURE__*/React.createElement(Box, { scroll: "vertical", flexible: true, shrink: true, dataId: `${dataId}_list`, preventParentScroll: "vertical", className: `${tabletMode ? style.responsivemaxHgt : style.maxHgt}`, onScroll: handleScroll, role: isSearch ? 'listbox' : 'menu', tabindex: "-1", isScrollAttribute: true }, optionsList.length != 0 && isDataLoaded ? /*#__PURE__*/React.createElement(React.Fragment, null, optionsList.map((item, i) => { const listItemText = item[keyName]; const isActive = value === listItemText; return /*#__PURE__*/React.createElement(StatusListItem, { key: i, dataId: `dataid_${i}`, value: listItemText, id: item[idName], active: isActive, onClick: e => onSelect(item, e), index: i, needTick: needTick, needBorder: false, bulletColor: item[statusColor], title: listItemText, needMultiLineText: needMultiLineText, autoHover: true, a11y: { role: isSearch ? 'option' : 'menuitem', ariaSelected: isActive, ariaLabel: listItemText } }); }), isFetchingOptions && /*#__PURE__*/React.createElement(Container, { isCover: false, align: "both" }, /*#__PURE__*/React.createElement(Loader, null))) : isDataLoaded ? /*#__PURE__*/React.createElement(CommonEmptyState, { className: style.svgWrapper, title: searchErrorText || 'No results', description: searchEmptyHint, size: "small", getEmptyState: emptySearchSVG }) : /*#__PURE__*/React.createElement("div", { className: style.loader }, /*#__PURE__*/React.createElement(Loader, null))), renderFooterElement ? renderFooterElement : null)); }) : null); } StatusDropdown.defaultProps = defaultProps; StatusDropdown.propTypes = propTypes; const StatusDropdown_Component = Popup(StatusDropdown); StatusDropdown_Component.defaultProps = defaultProps; StatusDropdown_Component.propTypes = propTypes; export default StatusDropdown_Component;