// // Copyright 2023 DXOS.org // import '@dxos/lit-ui/dx-avatar.pcss'; import { createContext } from '@radix-ui/react-context'; import { Primitive } from '@radix-ui/react-primitive'; import { Slot } from '@radix-ui/react-slot'; import React, { type ComponentProps, type ComponentPropsWithRef, forwardRef, type PropsWithChildren } from 'react'; import { type AvatarVariant, type AvatarStatus, type AvatarAnimation, type DxAvatar as NaturalDxAvatar, } from '@dxos/lit-ui'; import { DxAvatar } from '@dxos/lit-ui/react'; import { useId } from '@dxos/react-hooks'; import { mx } from '@dxos/react-ui-theme'; import { useIconHref, useThemeContext } from '../../hooks'; import { type ThemedClassName } from '../../util'; export type AvatarRootProps = PropsWithChildren>; type AvatarContextValue = { labelId: string; descriptionId: string; }; const AVATAR_NAME = 'Avatar'; const [AvatarProvider, useAvatarContext] = createContext(AVATAR_NAME); const AvatarRoot = ({ children, labelId: propsLabelId, descriptionId: propsDescriptionId }: AvatarRootProps) => { const labelId = useId('avatar__label', propsLabelId); const descriptionId = useId('avatar__description', propsDescriptionId); return {children}; }; type AvatarContentProps = ThemedClassName, 'children'>>; const AvatarContent = forwardRef( ({ icon, classNames, ...props }, forwardedRef) => { const href = useIconHref(icon); const { labelId, descriptionId } = useAvatarContext('AvatarContent'); return ( ); }, ); type AvatarLabelProps = ThemedClassName, 'id'>> & { asChild?: boolean; srOnly?: boolean; }; const AvatarLabel = forwardRef( ({ asChild, srOnly, classNames, ...props }, forwardedRef) => { const Root = asChild ? Slot : Primitive.span; const { tx } = useThemeContext(); const { labelId } = useAvatarContext('AvatarLabel'); return ( ); }, ); type AvatarDescriptionProps = ThemedClassName, 'id'>> & { asChild?: boolean; srOnly?: boolean; }; const AvatarDescription = forwardRef( ({ asChild, srOnly, classNames, ...props }, forwardedRef) => { const Root = asChild ? Slot : Primitive.span; const { tx } = useThemeContext(); const { descriptionId } = useAvatarContext('AvatarDescription'); return ( ); }, ); export const Avatar = { Root: AvatarRoot, Content: AvatarContent, Label: AvatarLabel, Description: AvatarDescription, }; export { useAvatarContext }; export type { AvatarStatus, AvatarVariant, AvatarAnimation, AvatarContentProps, AvatarLabelProps, AvatarDescriptionProps, NaturalDxAvatar as DxAvatar, };