import React, { useMemo } from "react"; import type { AccessibilityRole } from "react-native"; import { Pressable, View } from "react-native"; import type { IconNames } from "@jobber/design"; import { useStyles } from "./Chip.style"; import { Icon } from "../Icon"; import { Typography } from "../Typography"; import type { AtlantisThemeContextValue } from "../AtlantisThemeContext"; import { useAtlantisTheme } from "../AtlantisThemeContext"; export type AccentType = "client" | "invoice" | "job" | "request" | "quote"; export interface ChipProps { /** * label of the chip. */ readonly label?: string; /** * chip's active status */ readonly isActive: boolean; /** * Boolean for chip's ability to be dismissed */ readonly isDismissible?: boolean; /** * Background color to be used for inactive chips * * @default "background" */ readonly inactiveBackgroundColor?: "surface" | "background"; /** * Accessibility label for the component. It's also used for testing */ readonly accessibilityLabel?: string; /** * Accessibility role for the component */ readonly accessibilityRole?: AccessibilityRole; /** * Press handler */ onPress?(): void; /** * Optional Icon */ readonly icon?: IconNames; /** * Background color to be used for Active chips */ readonly accent?: AccentType; } export function Chip({ icon, label, onPress, isDismissible, isActive, inactiveBackgroundColor = "background", accessibilityLabel, accessibilityRole = "radio", accent, }: ChipProps) { const styles = useStyles(); const { tokens } = useAtlantisTheme(); const defaultAccentColor = tokens["color-surface--reverse"]; const { chipStyle, iconCustomColor, dismissColor } = useMemo(() => { const accentColor = accent ? tokens[`color-${accent}`] : defaultAccentColor; const iconColor = isActive ? tokens["color-surface"] : accentColor; const chip = [ styles.container, { backgroundColor: inactiveBackgroundColor === "surface" ? tokens["color-surface"] : tokens["color-interactive--background"], }, isActive && { backgroundColor: accentColor }, getBorderStyle(inactiveBackgroundColor, tokens), ]; const dismiss = (isActive || inactiveBackgroundColor === "surface") && styles.activeDismissIcon; return { chipStyle: chip, iconCustomColor: iconColor, dismissColor: dismiss, }; }, [accent, isActive, inactiveBackgroundColor, getBorderStyle, styles]); const accessibilityState = useMemo(() => { const checkableRoles = ["radio", "switch", "togglebutton", "checkbox"]; if (checkableRoles.includes(accessibilityRole)) { return { checked: isActive }; } return {}; }, [accessibilityRole, isActive]); return ( {icon && ( )} {label && ( {label} )} {isDismissible && ( )} ); } function getBorderStyle( inactiveBackgroundColor: "surface" | "background", tokens: AtlantisThemeContextValue["tokens"], ) { let borderColor = "transparent"; if (inactiveBackgroundColor === "surface") { borderColor = tokens["color-border"]; } return { borderColor, borderWidth: tokens["border-base"], }; }