Components
ElvixCard

ElvixCard

The chrome every SDK lives in. Brand-tinted border, Secured-by-elvix badge breakpoint, scrollable body + pinned footer pattern.

Welcome back

The brand-tinted border + Secured-by-elvix badge are part of the chrome — not decoration. Every elvix SDK lives inside this card.

components/username-pane.tsx
import { ElvixCard, ElvixUsername } from "@elvix.is/sdk/react";
export function UsernamePane() {
return (
<ElvixCard title="Pick a username">
{/* card={false} — the component would otherwise render its own card */}
<ElvixUsername card={false} />
</ElvixCard>
);
}

Props

PropTypeRequiredDefaultDescription
titlestringoptionalCard header text. Omit for headerless cards.
subtitlestringoptionalOne-line subtitle under the title.
childrenReact.ReactNoderequiredThe card body. Every <Elvix*> SDK component is designed to render inside.
footerReact.ReactNodeoptionalSecured-by-elvix badgePinned-bottom footer slot. Defaults to the Secured-by-elvix badge. Override with your own row.
size"sm" | "md" | "lg"optional"md"Width scale. Affects max-width and padding only.
tone"brand" | "neutral"optional"brand"Border + chord wash. Neutral for surfaces nested inside another brand chord.

The card paints from --elvix-primary, installed by <ElvixProvider>, so the chord stays in sync with your Console config without prop drilling.

Every SDK mutation component renders its own `<ElvixCard>` by default and accepts `card?: boolean` to drop it. ElvixIdentityForm, ElvixUsername, ElvixRegion, ElvixLanguages, ElvixAddressBook (+ the billing / shipping aliases), ElvixLegalEntities, ElvixSessions, ElvixAppPasskeys, ElvixExport, ElvixLeave, and ElvixDeactivate all default to card={true}. Pass card={false} when you're composing several into one shared card, or dropping a component into your own already-styled surface — the form renders bare, no border, no badge.

Mount animation (0.7.12+)

On mount, the card paints a brand-coloured trace that starts at the RIGHT edge of the Secured-by-elvix badge, draws clockwise around the perimeter, and ends at the badge's LEFT edge. Once the trace finishes, a static soft brand-tinted border fades in and the content settles. The Secured-by-elvix pill itself fades in first (200ms delay) so the badge is visible the moment the user sees the card.

Per-card override: <ElvixCard animated={false}> disables the animation for ONE card while leaving the rest of the surface animated. SDK-wide kill: <ElvixProvider animated={false}> disables motion across every nested <Elvix*> component in one move (implemented via framer-motion's MotionConfig reducedMotion="always"). When animated is left at its default the provider broadcasts reducedMotion="user", so the SDK respects the browser's prefers-reduced-motion automatically.

Realistic example

Title, subtitle, custom footer slot, and an explicit size. The card body is the slot every <Elvix*> component is designed to fit: sign-in, identity form, avatar editor, and so on.

components/profile-pane.tsx
import { ElvixCard, ElvixIdentityForm } from "@elvix.is/sdk/react";
export function ProfilePane() {
return (
<ElvixCard
title="Your profile"
subtitle="Visible to the apps you've signed into."
footer={<p className="text-[11px] text-fg-3">Powered by elvix</p>}
size="md"
>
<ElvixIdentityForm card={false} onSuccess={(u) => console.log("saved", u)} />
</ElvixCard>
);
}

Related