# Alert
A banner-style status surface: icon, title and description on a tinted severity fill, with a severity-aware live region.
## 1. Setup
```
// npm install class-variance-authority clsx tailwind-merge
```
File: `design-systems/andromeda-pro/components/Alert.tsx` · `'use client'` · `export const Alert` · `export const AlertIcon` · `export const AlertContent` · `export const AlertTitle` · `export const AlertDescription` · `export { alertVariants }`
```tsx
import { forwardRef } from 'react';
import type { ComponentPropsWithoutRef, ReactNode } from 'react';
import { cva } from 'class-variance-authority';
import type { VariantProps } from 'class-variance-authority';
import { cn, andromedaVars } from './lib/utils';
```
`./lib/utils` and `../tokens` are the Andromeda Pro tokens and lib, installed with the system: do not re-invent them. `cn` is `twMerge(clsx(...))`. `andromedaVars()` returns every token as a `--andromeda-*` custom property, which is how a Tailwind arbitrary value such as `p-[var(--andromeda-3)]` resolves at all.
## 2. Constants
```tsx
const alertVariants = cva(
[
'relative flex items-start gap-[var(--andromeda-1-5)]',
'p-[var(--andromeda-3)]',
'bg-[color:var(--alert-background)]',
'border-[length:var(--andromeda-border-width,1px)] border-solid',
'border-[color:var(--alert-border)]',
'rounded-[var(--andromeda-radius-frame,0px)]',
'[backdrop-filter:blur(var(--andromeda-blur-sm,2px))] [-webkit-backdrop-filter:blur(var(--andromeda-blur-sm,2px))]',
],
{
variants: {
variant: {
default: [
'[--alert-background:var(--andromeda-surface-raised)]',
'[--alert-border:var(--andromeda-border-base)]',
'[--alert-icon-color:var(--andromeda-text-secondary)]',
'[--alert-title-color:var(--andromeda-text-primary)]',
'[--alert-description-color:var(--andromeda-text-secondary)]',
],
accent: [
'[--alert-background:var(--andromeda-status-info-surface)]',
'[--alert-border:var(--andromeda-status-info-border)]',
'[--alert-icon-color:var(--andromeda-status-info-text)]',
'[--alert-title-color:var(--andromeda-status-info-on)]',
'[--alert-description-color:var(--andromeda-status-info-on-muted)]',
],
warning: [
'[--alert-background:var(--andromeda-status-warning-surface)]',
'[--alert-border:var(--andromeda-status-warning-border)]',
'[--alert-icon-color:var(--andromeda-status-warning-text)]',
'[--alert-title-color:var(--andromeda-status-warning-on)]',
'[--alert-description-color:var(--andromeda-status-warning-on-muted)]',
],
fault: [
'[--alert-background:var(--andromeda-status-danger-surface)]',
'[--alert-border:var(--andromeda-status-danger-border)]',
'[--alert-icon-color:var(--andromeda-status-danger-text)]',
'[--alert-title-color:var(--andromeda-status-danger-on)]',
'[--alert-description-color:var(--andromeda-status-danger-on-muted)]',
],
},
},
defaultVariants: { variant: 'default' },
},
);
export type AlertProps = ComponentPropsWithoutRef<'div'> &
VariantProps<typeof alertVariants> & {
children?: ReactNode;
};
```
The `status.info` tone is the brand blue: the prop is still spelled `accent`, only the token moved.State
- every hook, handler, effect and disposal
- the animation loop, frame by frame
Tree
- the JSX, every className and inline style
Why · Remix · Check
- the mechanism, the tuning points, the checks
Unlock Alert
The full source and the remix prompt ship with Premium.