UNPKG

@carbon/ibm-products

Version:
212 lines (210 loc) 8.62 kB
/** * 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. */ const require_runtime = require("../../../_virtual/_rolldown/runtime.js"); const require_util = require("../utils/util.js"); const require_ConditionBuilderProvider = require("../ConditionBuilderContext/ConditionBuilderProvider.js"); const require_ConditionBuilderButton = require("../ConditionBuilderButton/ConditionBuilderButton.js"); const require_translationObject = require("../ConditionBuilderContext/translationObject.js"); const require_useTranslations = require("../utils/useTranslations.js"); const require_handleKeyboardEvents = require("../utils/handleKeyboardEvents.js"); const require_useEvent = require("../utils/useEvent.js"); let react = require("react"); react = require_runtime.__toESM(react); let prop_types = require("prop-types"); prop_types = require_runtime.__toESM(prop_types); let _carbon_react = require("@carbon/react"); let _carbon_react_icons = require("@carbon/react/icons"); //#region src/components/ConditionBuilder/ConditionBuilderItem/ConditionBuilderItem.tsx /** * Copyright IBM Corp. 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. */ const ConditionBuilderItem = ({ children, className, label, renderIcon, title, type, showToolTip, condition, popOverClassName, config, renderChildren, onChange, description, ...rest }) => { const popoverRef = (0, react.useRef)(null); const [open, setOpen] = (0, react.useState)(false); const { conditionBuilderRef, statementConfigCustom, readOnly } = (0, react.useContext)(require_ConditionBuilderProvider.ConditionBuilderContext); const statementIdMap = { ifAll: require_translationObject.translationsObject.ifText, ifAny: require_translationObject.translationsObject.ifText, unlessAll: require_translationObject.translationsObject.unlessText, unlessAny: require_translationObject.translationsObject.unlessText }; statementConfigCustom?.forEach((statement) => { statementIdMap[statement.id] = statement.label; }); const [invalidText, addConditionText, addPropertyText, addOperatorText, addValueText, labelText] = require_useTranslations.useTranslations([ "invalidText", "addConditionText", "addPropertyText", "addOperatorText", "addValueText", label ], statementIdMap); const getCustomOperatorLabel = (propertyLabel) => { return propertyLabel && config?.operators?.find((operator) => { return operator.id === propertyLabel; }); }; const getPropertyDetails = () => { const { property, operator } = condition || {}; if (label === "INVALID" || rest["data-name"] === "propertyField" && property === "INVALID" || rest["data-name"] === "operatorField" && operator === "INVALID") return { propertyLabel: invalidText, isInvalid: true }; if (rest["data-name"] == "operatorField" && type == "custom") return { isInvalid: false, propertyLabel: getCustomOperatorLabel(label)?.id }; return { isInvalid: false, propertyLabel: rest["data-name"] == "valueField" && type ? require_util.getValue(type, label, config) : labelText }; }; const { propertyLabel, isInvalid } = getPropertyDetails(); (0, react.useEffect)(() => { /** * rest['data-name'] holds the current field name * popoverToOpen hold the next popover to be opened if required */ if (condition) { const currentField = rest["data-name"]; if (condition.popoverToOpen && currentField !== condition.popoverToOpen) closePopover(); else if (currentField == "valueField" && type === "option" && !require_util.checkForMultiSelectOperator(condition, config)) closePopover(); if (condition.popoverToOpen == currentField) setTimeout(() => { openPopOver(); }); } else closePopover(); }, [condition, label]); (0, react.useEffect)(() => { if (open && popoverRef.current) { const firstFocusableElement = popoverRef?.current?.querySelector("input,textarea"); if (firstFocusableElement) setTimeout(() => firstFocusableElement.focus(), 0); } }, [popoverRef, open]); require_useEvent.useEvent(popoverRef, "focusout", (event) => { const focusEvent = event; const relatedTarget = focusEvent.relatedTarget; const popoverEl = popoverRef.current; if (!popoverEl) return; const focusLeftPopover = relatedTarget && !popoverEl.contains(relatedTarget); const targetInsidePopover = popoverEl.contains(focusEvent.target); const focusMovedToDatePicker = focusEvent.target?.closest(".flatpickr-calendar"); if ((focusLeftPopover || !targetInsidePopover) && !focusMovedToDatePicker) closePopover(); }); const manageInvalidSelection = () => { if (rest["data-name"] === "propertyField" && !condition?.property || rest["data-name"] === "operatorField" && !condition?.operator || rest["data-name"] === "valueField" && !condition?.value) onChange?.("INVALID"); }; const closePopover = () => { if (open) manageInvalidSelection(); setOpen(false); }; const openPopOver = () => { if (readOnly) return; setOpen(true); }; const togglePopover = () => { if (children || renderChildren) setOpen(!open); }; const handleKeyDownHandler = (evt) => { require_handleKeyboardEvents.handleKeyDownForPopover(evt, conditionBuilderRef, popoverRef, closePopover); if (evt.key === "Escape") manageInvalidSelection(); }; const getLabel = () => { if (config?.operators && rest["data-name"] === "operatorField") return getCustomOperatorLabel(propertyLabel)?.label ?? addOperatorText; else if (propertyLabel) return propertyLabel; else if (rest["data-name"] === "propertyField") return addPropertyText; else if (rest["data-name"] === "operatorField") return addOperatorText; else if (rest["data-name"] === "valueField") return addValueText; else return addConditionText; }; return /* @__PURE__ */ react.default.createElement(_carbon_react.Popover, { open, isTabTip: true, role: "gridcell", className: `${popOverClassName} ${require_util.blockClass}__popover`, ref: popoverRef, onRequestClose: () => { if ((event?.target)?.closest(".flatpickr-calendar")) return; closePopover(); } }, /* @__PURE__ */ react.default.createElement(require_ConditionBuilderButton.ConditionBuilderButton, { label: getLabel(), hideLabel: !label ? true : false, onClick: togglePopover, className, "aria-haspopup": true, "aria-expanded": open, renderIcon: renderIcon ? renderIcon : label == void 0 ? _carbon_react_icons.Add : void 0, showToolTip, isInvalid, description, ...rest }), open && /* @__PURE__ */ react.default.createElement(_carbon_react.PopoverContent, { className: `${require_util.blockClass}__popover-content-wrapper`, role: "dialog", "aria-label": title, onKeyDown: handleKeyDownHandler }, /* @__PURE__ */ react.default.createElement(_carbon_react.Layer, null, /* @__PURE__ */ react.default.createElement(_carbon_react.Section, null, /* @__PURE__ */ react.default.createElement(_carbon_react.Heading, { className: `${require_util.blockClass}__item__title` }, title), /* @__PURE__ */ react.default.createElement("div", { className: `${require_util.blockClass}__popover-content` }, renderChildren ? renderChildren(popoverRef, closePopover) : children))))); }; ConditionBuilderItem.propTypes = { /** * provide the contents of the popover */ children: prop_types.default.node, /** * Provide an optional class to be applied to the containing node. */ className: prop_types.default.string, /** * current condition state object */ condition: prop_types.default.object, /** * this is the config object again the current property from inputConfig */ config: prop_types.default.object, /** * text to be displayed in the field */ label: prop_types.default.oneOfType([ prop_types.default.string, prop_types.default.array, prop_types.default.object ]), /** * callback to update the current condition of the state tree */ onChange: prop_types.default.func, /** * class name for popover */ popOverClassName: prop_types.default.string, /** * callback prop that returns the jsx for children */ renderChildren: prop_types.default.func, /** * Optional prop to allow overriding the icon rendering. */ renderIcon: prop_types.default.oneOfType([prop_types.default.func, prop_types.default.object]), /** * show tool tip */ showToolTip: prop_types.default.bool, /** * title of the popover */ title: prop_types.default.string, /** * input type */ type: prop_types.default.string }; //#endregion exports.ConditionBuilderItem = ConditionBuilderItem;