/*---------------------------------------------------------------------------------------------
 * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
 * See LICENSE.md in the project root for license terms and full copyright notice.
 *--------------------------------------------------------------------------------------------*/
/** @packageDocumentation
 * @module Notification
 */
import "./ElementTooltip.scss";
import classnames from "classnames";
import * as React from "react";
import * as ReactDOM from "react-dom";
import { UiEvent } from "@itwin/appui-abstract";
import { BeUiEvent } from "@itwin/core-bentley";
import { MessageRenderer, Rectangle } from "@itwin/core-react";
import { offsetAndContainInContainer, Tooltip } from "../layout/popup/Tooltip";
/** ElementTooltip Changed Event class.
 * @public
 * @deprecated in 4.13.0. This class should not be used by applications to instantiate objects.
 */
export class ElementTooltipChangedEvent extends UiEvent {
}
/** ElementTooltip React component.
 * @public
 */
export class ElementTooltip extends React.Component {
    static get onElementTooltipChangedEvent() {
        return ElementTooltip._elementTooltipChangedEvent;
    }
    static get isTooltipVisible() {
        return ElementTooltip._isTooltipVisible;
    }
    static showTooltip(el, message, pt, options) {
        if (ElementTooltip._isTooltipHalted)
            return;
        ElementTooltip._isTooltipVisible = true;
        ElementTooltip.onElementTooltipChangedEvent.emit({
            isTooltipVisible: true,
            el,
            message,
            pt,
            options,
        });
    }
    static hideTooltip() {
        ElementTooltip._isTooltipVisible = false;
        ElementTooltip.onElementTooltipChangedEvent.emit({
            isTooltipVisible: false,
            message: "",
        });
    }
    static get isTooltipHalted() {
        return ElementTooltip._isTooltipHalted;
    }
    static set isTooltipHalted(halt) {
        ElementTooltip._isTooltipHalted = halt;
        if (halt && ElementTooltip._isTooltipVisible)
            ElementTooltip.hideTooltip();
    }
    render() {
        return React.createElement(ElementTooltipComponent, null);
    }
}
ElementTooltip._elementTooltipChangedEvent = new BeUiEvent();
function ElementTooltipComponent(props) {
    const [visible, setVisible] = React.useState(false);
    const [message, setMessage] = React.useState("");
    const [preferredPosition, setPreferredPosition] = React.useState(undefined);
    const [position, setPosition] = React.useState({ x: 0, y: 0 });
    // Use a dedicated container for the tooltip to avoid z-index issues in the main window.
    const [mainContainer, setMainContainer] = React.useState(undefined);
    const [container, setContainer] = React.useState(undefined);
    const [popout, setPopout] = React.useState(false);
    const [size, setSize] = React.useState(undefined);
    React.useEffect(() => {
        return ElementTooltip.onElementTooltipChangedEvent.addListener((args) => {
            const isPopout = args.el?.ownerDocument.defaultView !== window;
            setPopout(isPopout);
            setVisible(args.isTooltipVisible);
            setMessage(args.message);
            setContainer(args.el);
            setPreferredPosition(args.pt);
        });
    }, []);
    const portalContainer = popout ? container : mainContainer;
    React.useLayoutEffect(() => {
        if (!preferredPosition)
            return;
        // Use preferred position by default.
        setPosition(preferredPosition);
        if (!container)
            return;
        if (!size)
            return;
        // Contain the tooltip based on the container bounds.
        const containerBounds = Rectangle.create(container.getBoundingClientRect());
        const bounds = Rectangle.createFromSize(size).offset(preferredPosition);
        const adjustedPosition = offsetAndContainInContainer(bounds, containerBounds.getSize(), { x: 8, y: 8 });
        const newPosition = adjustedPosition.offset(containerBounds.topLeft());
        setPosition(newPosition);
    }, [container, size, preferredPosition]);
    return (React.createElement(React.Fragment, null,
        React.createElement("div", { className: classnames("uifw-feedback-elementTooltip_container", props.className), ref: (el) => setMainContainer(el ?? undefined) }),
        portalContainer &&
            visible &&
            ReactDOM.createPortal(React.createElement(Tooltip, { className: classnames("uifw-feedback-elementTooltip", props.className), style: props.style, onSizeChanged: setSize, position: position },
                React.createElement(MessageRenderer, { message: message })), portalContainer)));
}
//# sourceMappingURL=ElementTooltip.js.map