/**
 * 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 { blockClass, checkForMultiSelectOperator, getValue } from "../utils/util.js";
import { ConditionBuilderContext } from "../ConditionBuilderContext/ConditionBuilderProvider.js";
import { ConditionBuilderButton } from "../ConditionBuilderButton/ConditionBuilderButton.js";
import { translationsObject } from "../ConditionBuilderContext/translationObject.js";
import { useTranslations } from "../utils/useTranslations.js";
import { handleKeyDownForPopover } from "../utils/handleKeyboardEvents.js";
import { useEvent } from "../utils/useEvent.js";
import React, { useContext, useEffect, useRef, useState } from "react";
import PropTypes from "prop-types";
import { Heading, Layer, Popover, PopoverContent, Section } from "@carbon/react";
import { Add } from "@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 = useRef(null);
	const [open, setOpen] = useState(false);
	const { conditionBuilderRef, statementConfigCustom, readOnly } = useContext(ConditionBuilderContext);
	const statementIdMap = {
		ifAll: translationsObject.ifText,
		ifAny: translationsObject.ifText,
		unlessAll: translationsObject.unlessText,
		unlessAny: translationsObject.unlessText
	};
	statementConfigCustom?.forEach((statement) => {
		statementIdMap[statement.id] = statement.label;
	});
	const [invalidText, addConditionText, addPropertyText, addOperatorText, addValueText, labelText] = 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 ? getValue(type, label, config) : labelText
		};
	};
	const { propertyLabel, isInvalid } = getPropertyDetails();
	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" && !checkForMultiSelectOperator(condition, config)) closePopover();
			if (condition.popoverToOpen == currentField) setTimeout(() => {
				openPopOver();
			});
		} else closePopover();
	}, [condition, label]);
	useEffect(() => {
		if (open && popoverRef.current) {
			const firstFocusableElement = popoverRef?.current?.querySelector("input,textarea");
			if (firstFocusableElement) setTimeout(() => firstFocusableElement.focus(), 0);
		}
	}, [popoverRef, open]);
	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) => {
		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.createElement(Popover, {
		open,
		isTabTip: true,
		role: "gridcell",
		className: `${popOverClassName} ${blockClass}__popover`,
		ref: popoverRef,
		onRequestClose: () => {
			if ((event?.target)?.closest(".flatpickr-calendar")) return;
			closePopover();
		}
	}, /* @__PURE__ */ React.createElement(ConditionBuilderButton, {
		label: getLabel(),
		hideLabel: !label ? true : false,
		onClick: togglePopover,
		className,
		"aria-haspopup": true,
		"aria-expanded": open,
		renderIcon: renderIcon ? renderIcon : label == void 0 ? Add : void 0,
		showToolTip,
		isInvalid,
		description,
		...rest
	}), open && /* @__PURE__ */ React.createElement(PopoverContent, {
		className: `${blockClass}__popover-content-wrapper`,
		role: "dialog",
		"aria-label": title,
		onKeyDown: handleKeyDownHandler
	}, /* @__PURE__ */ React.createElement(Layer, null, /* @__PURE__ */ React.createElement(Section, null, /* @__PURE__ */ React.createElement(Heading, { className: `${blockClass}__item__title` }, title), /* @__PURE__ */ React.createElement("div", { className: `${blockClass}__popover-content` }, renderChildren ? renderChildren(popoverRef, closePopover) : children)))));
};
ConditionBuilderItem.propTypes = {
	children: PropTypes.node,
	className: PropTypes.string,
	condition: PropTypes.object,
	config: PropTypes.object,
	label: PropTypes.oneOfType([
		PropTypes.string,
		PropTypes.array,
		PropTypes.object
	]),
	onChange: PropTypes.func,
	popOverClassName: PropTypes.string,
	renderChildren: PropTypes.func,
	renderIcon: PropTypes.oneOfType([PropTypes.func, PropTypes.object]),
	showToolTip: PropTypes.bool,
	title: PropTypes.string,
	type: PropTypes.string
};

//#endregion
export { ConditionBuilderItem };