const FormExample01 = () => {
    const [organization, setOrganization] = React.useState(0);
    return (
        <Form>
            <Headline el="div" className="m-b-4">Add Contact</Headline>
            <Form.Group widths="equal">
                <Form.Input label="First Name" placeholder="Leia" />
                <Form.Input label="Last Name" placeholder="Organa" />
            </Form.Group>
            <Form.AnvilSelect
                label="Home Planet"
                trigger={{
                    placeholder: "Choose Planet"
                }}
                options={[
                    {key:1, value: 1, text: 'Alderaan'},
                    {key:2, value: 2, text: 'Bespin'},
                    {key:3, value: 3, text: 'Coruscant'},
                    {key:4, value: 4, text: 'Dagobah'},
                    {key:5, value: 5, text: 'Hoth'},
                    {key:6, value: 6, text: 'Kashyyyk'},
                    {key:7, value: 7, text: 'Naboo',},
                    {key:8, value: 8, text: 'Tatooine'},
                    {key:9, value: 9, text: 'Yavin'},
                ]}
            />
            <Form.Field>
                <Grid columns="equal">
                    <Grid.Column>
                        <Form.Group grouped>
                            <label>Organization</label>
                            <Form.Radio
                                label="Rebel Alliance"
                                value="1"
                                checked={organization === 1}
                                onChange={() => setOrganization(1)}
                            />
                            <Form.Radio
                                label="Galactic Empire"
                                value="2"
                                checked={organization === 2}
                                onChange={() => setOrganization(2)}
                            />
                            <Form.Radio
                                label="Trade Federation"
                                value="3"
                                checked={organization === 3}
                                onChange={() => setOrganization(3)}
                            />
                        </Form.Group>
                    </Grid.Column>
                    <Grid.Column>
                        <Form.Group grouped>
                            <label>Attributes</label>
                            <Form.Checkbox label="Force User" />
                            <Form.Checkbox label="Pilot" />
                            <Form.Checkbox label="Bounty Hunter" />
                        </Form.Group>
                    </Grid.Column>
                </Grid>
            </Form.Field>
            <Form.TextArea label="Quotes" placeholder="Aren't you a little short for a stormtrooper?" />
            <Form.Group>
                <Form.Button primary>Save Contact</Form.Button>
                <Form.Button>Cancel</Form.Button>
            </Form.Group>
        </Form>
    )
}
render (FormExample01)

Labels

Components within a Form have a few labeling options.

<Form>
    <Form.Input
        label="Input Label"
    />
</Form>
<Form>
    <Form.Checkbox
        label="Checkbox Label"
    />
    <Form.Radio
        label="Radio Label"
    />
</Form>
<Form>
    <Form.AnvilSelect
        label="Select Label"
        options={[]}
    />
</Form>

Label Help

Labels can have a help icon with a tooltip to provide additional context to a label.

<Form>
    <Form.Input
        label="Input Label"
        labelProps={{
            help: "This is help text"
        }}
    />
</Form>
<Form>
    <Form.Checkbox
        label="Checkbox Label"
        labelProps={{
            help: "This is help text"
        }}
    />
    <Form.Radio
        label="Radio Label"
        labelProps={{
            help: "This is help text"
        }}
    />
</Form>
<Form>
    <Form.AnvilSelect
        label="Select Label"
        labelProps={{
            help: "The tooltip direction can also be controlled",
            direction: "b"
        }}
        options={[]}
    />
</Form>

Required and Optional

A visual indicator can be applied on a form's label.

<Form>
    <Form.Input
        label="Required Label"
        labelProps={{
            required: true
        }}
    />
    <Form.Input
        label="Required Label"
        labelProps={{
            help: "Help and required next to each other",
            required: true
        }}
    />
</Form>
<Form>
    <Form.Input
        label="Optional Label"
        labelProps={{
            optional: true
        }}
    />
    <Form.Input
        label="Optional Label"
        labelProps={{
            help: "Help and optional next to each other",
            optional: true
        }}
    />
</Form>

Label Action

An action can be applied to certain forms. This action is a closely related secondary option to the field.

<Form>
    <Form.Input
        label="Field Label"
        labelProps={{
            action: <Link primary onClick={() => alert('Label action triggered')}>Label Action</Link>
        }}
    />
</Form>
const FormExample02 = () => {
    const [open, setOpen] = React.useState(false)
    return (
        <Form>
            <Form.Input
                label="Field Label"
                labelProps={{
                    action: (
                        <Stack justifyContent="center">
                            <Popover
                                header={<BodyText size="small">Popover Header</BodyText>}
                                headerAlign="space-between"
                                trigger={<Link primary onClick={() => setOpen(!open)}>Popover Action</Link>}
                                footer={<BodyText size="small">Popover Footer</BodyText>}
                                open={open}
                                direction="tl"
                                width="xs"
                            >
                                <div>
                                    <BodyText size="small">Popover content.</BodyText>
                                    <BodyText size="small">Second line of text.</BodyText>
                                </div>
                            </Popover>
                        </Stack>
                    )
                }}
            />
        </Form>
    )
}
render (FormExample02)
const FormExample03 = () => {
    const [open, setOpen] = React.useState(false)

    return (
        <div>
            <Modal
                closable={true}
                onClose={() => setOpen(false)}
                open={open}
                title="Accept Estimate"
                footer={<Button primary onClick={() => setOpen(false)}>Submit</Button>}
            >
                This is a modal that was triggered by an action.
            </Modal>

            <Form>
                <Form.Input
                    label="Field Label"
                    labelProps={{
                        action: <Link primary onClick={() => setOpen(true)}>Modal Action</Link>
                    }}
                />
            </Form>
        </div>
    )
}
render (FormExample03)
const FormExample04 = () => {
    const [open, setOpen] = React.useState(false)

    return (
        <div>
            <Drawer
                header="Drawer Header"
                open={open}
                onClose={() => setOpen(false)}
            >
                Content related to the field.
            </Drawer>

            <Form>
                <Form.Input
                    label="Field Label"
                    labelProps={{
                        action: <Link primary onClick={() => setOpen(!open)}>Drawer Action</Link>
                    }}
                />
            </Form>
        </div>
    )
}

render (FormExample04)

Errors

Forms can provide a visual for errors.

<Form
    style={{
        display: 'grid',
        gridTemplateColumns: '1fr 1fr',
        gridRowGap: '16px',
        gridColumnGap: '16px',
        justifyItems: 'stretch',
        alignItems: 'start'
    }}
>
    <Form.Input
        label="Input Label"
        value="Input value"
        error="This is error text"
    />
    <Form.AnvilSelect
        label="Select Label"
        placeholder="Select value"
        error="This is error text"
        options={[]}
    />
    <Form.Radio
        label="Field Label"
        value="Input value"
        error="This is error text"
    />
    <Form.Checkbox
        label="Field Label"
        value="Input value"
        error="This is error text"
    />
</Form>
<Form>
    <Form.Input
        label="Input Label"
        value="Input value"
        error={
            <Stack className="m-t-2" alignItems="flex-start">
                <Icon name="warning" size={18} className="c-red-500 m-r-1" />
                <Stack direction="column">
                    <BodyText className="c-red-500 m-b-1 lh-1" size="small"> This is a custom made error message</BodyText>
                    <BodyText className="c-red-500 lh-1" size="small">This is a second line of errors</BodyText>
                </Stack>
            </Stack>
        }
    />
</Form>

Field Descriptions

A form can also have description content below the control. This content can be useful to provide context to the user.

<Form
    style={{
        display: 'grid',
        gridTemplateColumns: '1fr 1fr',
        gridRowGap: '32px',
        gridColumnGap: '32px',
        justifyItems: 'stretch',
        alignItems: 'start'
    }}
>
    <Form.Input
        label="Name"
        value="John Doe"
        description="Your name may appear around the site."
    />
    <Form.Input
        label="Password"
        type="Password"
        value="123456"
        description={
            <React.Fragment>
                <BodyText subdued size="small" className="m-t-2 m-b-half">Use 8 or more characters</BodyText>
                <BodyText subdued size="small" className="m-b-half">Use at least one uppercase and one lowercase letter (Aa)</BodyText>
                <BodyText subdued size="small">Use at least one digit (0-9)</BodyText>
            </React.Fragment>
        }
    />
    <Form.ToggleSwitch
        label="Show Job History"
        placeholder="Select value"
        description="Enabling this will show job information to everyone who has access to project history."
    />
    <Form.Checkbox
        label="XLS"
        size="large"
        description="Only supports version X, Y, and Z."
    />
    <Form.Input
        label="Description and Error"
        value="Input Value"
        description="Description text in relation to error text"
        error="This is an error message"
    />
</Form>

Related Components


Importing

import { Form } from '@servicetitan/design-system';