A form control that allows the user to toggle between checked and not checked. Supports indeterminate state.
import { Checkbox } from "@ngrok/mantle/checkbox";
import { Label } from "@ngrok/mantle/label";
<Label htmlFor="terms" className="flex items-center gap-2">
<Checkbox name="terms" id="terms" />
Accept terms and conditions
</Label>
<Label htmlFor="unchecked" className="flex items-center gap-2">
<Checkbox id="unchecked" name="unchecked" checked={false} readOnly />
Unchecked
</Label>
<Label htmlFor="checked" className="flex items-center gap-2">
<Checkbox id="checked" name="checked" checked readOnly />
Checked
</Label>
<Label htmlFor="indeterminate" className="flex items-center gap-2">
<Checkbox id="indeterminate" name="indeterminate" defaultChecked="indeterminate" readOnly />
Indeterminate
</Label>The Checkbox can be used in forms with client-side validation. Here's an example using @tanstack/react-form and zod:
import { Button } from "@ngrok/mantle/button";
import { Label } from "@ngrok/mantle/label";
import { Checkbox } from "@ngrok/mantle/checkbox";
import { useForm } from "@tanstack/react-form";
import { z } from "zod";
const formSchema = z.object({
acceptedTermsAndConditions: z
.boolean()
.refine((value) => value, "You must accept the terms and conditions."),
});
function FormExample() {
const form = useForm({
defaultValues: {
acceptedTermsAndConditions: false,
},
validators: {
onSubmit: formSchema,
},
onSubmit: ({ value }) => {
// Handle form submission here
},
});
return (
<form
className="space-y-4"
onSubmit={(event) => {
event.preventDefault();
event.stopPropagation();
void form.handleSubmit();
}}
>
<div className="space-y-1">
<form.Field name="acceptedTermsAndConditions">
{(field) => (
<Label htmlFor={field.name} className="flex items-center gap-2">
<Checkbox
name={field.name}
id={field.name}
checked={field.state.value}
onBlur={field.handleBlur}
onChange={(event) => field.handleChange(event.target.checked)}
validation={field.state.meta.errors.length > 0 && "error"}
/>
Accept terms and conditions
</Label>
)}
</form.Field>
</div>
<form.Subscribe selector={(state) => state.isDirty}>
{(isDirty) => (
<Button type="submit" appearance="filled" disabled={!isDirty}>
Submit
</Button>
)}
</form.Subscribe>
</form>
);
}All props from input[type="checkbox"], plus: