Field
A label, a control and a hint make a field; Fieldset and Form group fields into a form.
import { Field, Fieldset, Legend, Form } from '@iffday/ui';Field
Field stacks a label, a control and a hint: the label is 13px and medium weight, the hint is secondary text. Base UI ties the label to the control, so a screen reader reads the label as the control’s name.
Use 1–30 letters, numbers, underscores or periods. Your preferred casing is retained. Do not start or end with a period, or use consecutive periods. Other users may reuse a previous handle.
import { useT } from '@iffday/i18n';
import { Field, Input } from '@iffday/ui';
export default function Example() {
const t = useT();
return (
<div style={{ width: 'min(100%, 380px)' }}>
<Field label={t('account.settings.displayName')}>
<Input defaultValue="Lin" />
</Field>
<Field
label={t('account.profile.profileHandle')}
hint={t('account.profile.useLettersNumbersUnderscoresOrPeriodsYourPreferredCasing')}
>
<Input defaultValue="lin" />
</Field>
</div>
);
}Form
Form checks constraints such as required and pattern before it submits, and the browser points at the field that fails. Group related fields in a Fieldset named by a Legend. After a save, tell the reader with a toast: Save in the example below shows Saved.
import { useT } from '@iffday/i18n';
import { Button, Field, Fieldset, Form, Input, Legend, Textarea } from '@iffday/ui';
import { useApp } from '@iffday/web/src/state';
export default function Example() {
const t = useT();
const { notify } = useApp();
return (
<Form
style={{ width: 'min(100%, 420px)' }}
onSubmit={(event) => {
event.preventDefault();
notify(t('common.saved'));
}}
>
<Fieldset>
<Legend>{t('nav.myProfile')}</Legend>
<Field label={t('account.settings.displayName')}>
<Input name="name" required defaultValue="Lin" />
</Field>
<Field label={t('account.profile.profileHandle')}>
<Input name="handle" required pattern="[A-Za-z0-9_.]{1,30}" defaultValue="lin" />
</Field>
<Field label={t('account.settings.bio')}>
<Textarea name="bio" rows={3} />
</Field>
</Fieldset>
<div style={{ display: 'flex', gap: 8 }}>
<Button className="button primary">{t('common.save')}</Button>
<Button type="reset" className="button neutral">
{t('common.cancel')}
</Button>
</div>
</Form>
);
}Props
| Prop | Type | Default |
|---|---|---|
label* | string | |
children* | ReactNode | |
hint | string |
- src/pages/cms.tsx26
- src/pages/cms-festivals.tsx23
- src/pages/personal.tsx14
- src/pages/editorial.tsx13
- src/pages/film-images.tsx13
- src/pages/auth.tsx8
- src/pages/planner-settings.tsx8
- src/pages/account-settings.tsx6
- src/pages/catalog-drafts.tsx4
- src/pages/social.tsx4
- src/pages/archive-tools.tsx3
- src/pages/film-entry.tsx2
- src/pages/programme.tsx2
- src/pages/wallet-extras.tsx2
- src/film-media.tsx1
- src/pages/cms-addresses.tsx1
- src/pages/profile.tsx1
Fieldset
packages/ui/src/controls.tsx:45Exports BaseFieldset.Root as it is, with Base UI’s props (see the Base UI documentation).
Other props go to ComponentProps<'legend'>.
Exports BaseForm as it is, with Base UI’s props (see the Base UI documentation).
- src/pages/cms-festivals.tsx10
- src/pages/cms.tsx6
- src/pages/auth.tsx5
- src/pages/personal.tsx4
- src/pages/cms-addresses.tsx3
- src/pages/film-entry.tsx3
- src/pages/social.tsx3
- src/pages/account-settings.tsx2
- src/pages/editorial.tsx2
- src/pages/film-images.tsx2
- src/pages/planner-settings.tsx2
- src/pages/profile.tsx2
- src/App.tsx1
- src/pages/archive-tools.tsx1
- src/pages/catalog-drafts.tsx1
- src/pages/search.tsx1
- src/pages/wallet-extras.tsx1
- src/review-card.tsx1