Field
Keep a label, input, help text and validation message together.
import { … } from "@fungi.computer/caps/components/field";Hero
import { Field } from "@fungi.computer/caps/components/field";import { Input } from "@fungi.computer/caps/components/input";
export default function Hero() { return ( <Field description="Shown to other foragers near you." label="Display name"> <Input defaultValue="Spore Scout" name="displayName" /> </Field> );}Orientations
import { Field } from "@fungi.computer/caps/components/field";import { Input } from "@fungi.computer/caps/components/input";import { Switch } from "@fungi.computer/caps/components/switch";
export default function Orientations() { return ( <div className="flex w-full max-w-sm flex-col gap-4"> <Field label="Radius" orientation="horizontal"> <Input className="w-24" defaultValue="5 mi" name="radius" /> </Field> <Field label="Notify on new spots" orientation="inline"> <Switch defaultChecked name="notify" /> </Field> </div> );}Validation
import { useState } from "react";import { Field } from "@fungi.computer/caps/components/field";import { Input } from "@fungi.computer/caps/components/input";
export default function Validation() { const [value, setValue] = useState(""); const error = value.length > 0 && value.length < 3 ? "Too short" : undefined; return ( <Field error={error} label="Club name" required> <Input onChange={(event) => { setValue(event.target.value); }} value={value} /> </Field> );}Number field
import { useState } from "react";import { Field, NumberField } from "@fungi.computer/caps/components/field";
export default function Quantity() { const [count, setCount] = useState<number | null>(3); return ( <Field label="Baskets to bring"> <NumberField max={10} min={0} onValueChange={setCount} value={count} /> </Field> );}Props
FormFooterProps
| Prop | Type | Description |
|---|---|---|
error? | ReactNode | The submit-time error, announced above the actions. |
layout? | "end" | | end right-aligns actions; stretch stacks full-width actions for single-column cards. |
status? | ReactNode | Quiet state opposite the actions (role="status"), such as a Status LED reading "Saved". |
divider? | boolean | Draws the rule above the footer; short inline forms leave it off. |
error?ReactNodeThe submit-time error, announced above the actions.
layout?"end" |"stretch" end right-aligns actions; stretch stacks full-width actions for single-column cards.
status?ReactNodeQuiet state opposite the actions (role="status"), such as a Status LED reading "Saved".
divider?booleanDraws the rule above the footer; short inline forms leave it off.
FormProps
| Prop | Type | Description |
|---|---|---|
busy? | boolean | Disables every control while a submission is in flight. |
busy?booleanDisables every control while a submission is in flight.
FormSectionProps
| Prop | Type | Description |
|---|---|---|
title | ReactNode | |
description? | ReactNode | |
level? | 2 | | Heading level inside the page outline. |
children | ReactNode |
titleReactNodedescription?ReactNodelevel?2 |3 | 4 Heading level inside the page outline.
childrenReactNode
FieldSetProps
| Prop | Type | Description |
|---|---|---|
legend | ReactNode | |
description? | ReactNode | |
error? | ReactNode | The group's announced error, such as "Choose at least one right". |
children | ReactNode |
legendReactNodedescription?ReactNodeerror?ReactNodeThe group's announced error, such as "Choose at least one right".
childrenReactNode
FieldProps
| Prop | Type | Description |
|---|---|---|
children | ReactNode | |
description? | ReactNode | |
error? | ReactNode | |
icon? | ReactNode | A decorative marker, such as a Sigil or App icon, before the label. It is hidden from assistive tech; the label stays the control's name. |
label? | ReactNode | |
orientation? | "horizontal" | | vertical stacks label, control and error; horizontal puts the control opposite its copy (settings rows); inline puts a checkbox or switch before its copy. |
optional? | boolean | Marks an optional field in a mostly required form. |
readout? | boolean | The child is a read-only readout, such as a Status, not a control: the label names the row and nothing is wired to the child. |
required? | boolean |
childrenReactNodedescription?ReactNodeerror?ReactNodeicon?ReactNodeA decorative marker, such as a Sigil or App icon, before the label. It is hidden from assistive tech; the label stays the control's name.
label?ReactNodeorientation?"horizontal" |"inline" | "vertical" vertical stacks label, control and error; horizontal puts the control opposite its copy (settings rows); inline puts a checkbox or switch before its copy.
optional?booleanMarks an optional field in a mostly required form.
readout?booleanThe child is a read-only readout, such as a Status, not a control: the label names the row and nothing is wired to the child.
required?boolean
NumberFieldProps
| Prop | Type | Description |
|---|---|---|
value? | number | | Controlled value; null is empty. |
defaultValue? | number | | |
onValueChange()? | (value) => void | Called with each committed value, already clamped to min/max. |
min? | number | |
max? | number | |
step? | number | Arrow keys and the − / + keys move by step; Page Up/Down by ten steps. |
unit? | ReactNode | A short unit readout after the value, such as "min" or "GB". |
wrap? | boolean | Cycle from max back to min (and back) instead of stopping at the ends. |
invalid? | boolean | |
decrementLabel? | string | Accessible names for the − / + keys. |
incrementLabel? | string |
value?number |null Controlled value; null is empty.
defaultValue?number |null onValueChange()?(value) => voidCalled with each committed value, already clamped to min/max.
min?numbermax?numberstep?numberArrow keys and the − / + keys move by step; Page Up/Down by ten steps.
unit?ReactNodeA short unit readout after the value, such as "min" or "GB".
wrap?booleanCycle from max back to min (and back) instead of stopping at the ends.
invalid?booleandecrementLabel?stringAccessible names for the − / + keys.
incrementLabel?string
Full types: API reference.