import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
import { forwardRef, useState, useEffect, useMemo } from 'react';
import styled, { css } from 'styled-components';
import { rgba } from 'polished';
import Image from '../Image';
import { defaultThemeProp } from '../../theme';
import Icon, { StyledIcon } from '../Icon';
import { Alert } from '../Badges';
import { useI18n, useTestIds } from '../../hooks';
import { tryCatch, withTestIds } from '../../utils';
import { readableColor } from '../../styles';
import { getAvatarTestIds } from './Avatar.test-ids';
const sizeToRem = {
    s: 1,
    m: 2,
    l: 2.5,
    xl: 4
};
const fontSizeToRem = {
    s: 0.5625,
    m: 0.8125,
    l: 1,
    xl: 1.5
};
export const StyledAvatarImage = styled(Image) `
  min-height: 100%;
  min-width: 100%;
  aspect-ratio: 1 / 1;
  object-fit: cover;
  border-radius: inherit;
  height: fit-content;
  width: fit-content;
`;
export const StyledAvatar = styled.div(({ hasBrokenImage, hasSrc, size, shape, color, backgroundColor, theme: { base: { palette: { 'foreground-color': foregroundColor, 'primary-background': primaryBackground }, 'border-radius': baseBorderRadius }, components: { avatar: { 'background-color': avatarBackground }, icon: { 'border-radius-multiplier': borderRadiusMultiplier } } } }) => {
    const sizeRem = sizeToRem[size];
    const fontSize = fontSizeToRem[size];
    let bgColor = hasSrc && !hasBrokenImage ? primaryBackground : backgroundColor || avatarBackground;
    if (color && !backgroundColor && !(hasSrc && !hasBrokenImage))
        bgColor = tryCatch(() => readableColor(color), () => avatarBackground);
    const shadowColor = tryCatch(() => rgba(foregroundColor, 0.1));
    const iconColor = color || tryCatch(() => readableColor(bgColor));
    return css `
      position: relative;
      flex-shrink: 0;
      background-color: ${bgColor};
      color: ${iconColor};
      width: ${sizeRem}rem;
      height: ${sizeRem}rem;
      min-width: ${sizeRem}rem;
      min-height: ${sizeRem}rem;
      font-size: ${fontSize}rem;
      text-transform: uppercase;
      line-height: ${sizeRem}rem;
      text-align: center;
      vertical-align: top;
      display: inline-block;
      border-radius: 100%;
      user-select: none;
      -webkit-user-select: none;

      ${shape === 'squircle' &&
        css `
        border-radius: calc(${borderRadiusMultiplier} * ${baseBorderRadius});
      `}

      ${StyledIcon} {
        width: 50%;
        height: 100%;
        vertical-align: initial;
      }

      ::after {
        content: '';
        position: absolute;
        inset: 0;
        border-radius: inherit;
        pointer-events: none;
        box-shadow: inset 0 0 0 0.0625rem ${shadowColor};
      }
    `;
});
StyledAvatar.defaultProps = defaultThemeProp;
export const StyledStatus = styled(Alert)(({ size, theme }) => {
    /** Scales alert badge dimensions based on size of avatar */
    const sizeDimensions = (0.625 * sizeToRem[size]) / sizeToRem.m;
    return css `
    position: absolute;
    height: ${sizeDimensions}rem;
    width: ${sizeDimensions}rem;
    inset-block-end: 0;
    inset-inline-end: 0;
    z-index: 1;
    animation: pop calc(${theme.base.animation.speed} * 2) cubic-bezier(1, 1.65, 0.3, 1.24);

    @keyframes pop {
      0% {
        opacity: 0;
        transform: scale(0);
      }
      50% {
        opacity: 1;
      }
      100% {
        transform: scale(1);
      }
    }
  `;
});
StyledStatus.defaultProps = defaultThemeProp;
/**
 * Helper function to construct a two or one letter initial from the title prop.
 * This text will be displayed if no valid image source is provided.
 * @param name
 * @param size
 */
const getInitials = (name, size) => {
    const words = name.split(' ');
    const firstInitial = words[0][0];
    return words.length === 1 || size === 's' ? firstInitial : `${firstInitial}${words[1][0]}`;
};
/**
 * Generally, avatars are used to distinguish between different operators and
 * objects when they are shown in a list or in a small space. Users of applications
 * can upload a custom avatar of their choice.
 */
const Avatar = forwardRef(function Avatar(props, ref) {
    const { testId, shape = 'circle', size = 'm', imageSrc, icon, name, status, onImageError, ...restProps } = props;
    const [hasBrokenImage, setHasBrokenImage] = useState();
    const t = useI18n();
    const testIds = useTestIds(testId, getAvatarTestIds);
    useEffect(() => {
        setHasBrokenImage(undefined);
    }, [imageSrc]);
    const content = useMemo(() => {
        if (icon) {
            return _jsx(Icon, { name: icon });
        }
        if (imageSrc && !hasBrokenImage) {
            return (_jsx(StyledAvatarImage, { src: imageSrc, alt: name, onError: (e) => {
                    setHasBrokenImage(true);
                    onImageError?.(e);
                }, onLoad: () => {
                    setHasBrokenImage(false);
                } }));
        }
        return getInitials(name, size);
    }, [imageSrc, name, size, icon, hasBrokenImage, onImageError]);
    return (_jsxs(StyledAvatar, { "data-testid": testIds.root, role: 'img', hasSrc: !!imageSrc, hasBrokenImage: hasBrokenImage, shape: shape, size: size, ref: ref, "aria-label": `${name}${status ? ` ${t('status')} ${status}` : ''}`, ...restProps, children: [content, status === 'active' && _jsx(StyledStatus, { size: size, variant: 'success' })] }));
});
export default withTestIds(Avatar, getAvatarTestIds);
//# sourceMappingURL=Avatar.js.map