RHFTextarea
Multi-line text input component integrated with React Hook Form
You are reading the v1 docs. v2 renamed several props and replaced GeckoUIPortal with GeckoUIProvider. Read this page in v2.
Live examples are only rendered in the v2 docs.
RHFTextarea
A multi-line textarea component integrated with React Hook Form that automatically displays error states with a red border when validation fails. Supports auto-resizing functionality.
Installation
import { RHFTextarea } from '@geckoui/geckoui';Basic Usage
import { useForm, FormProvider } from 'react-hook-form';
import { RHFTextarea } from '@geckoui/geckoui';
function Example() {
const methods = useForm({
defaultValues: {
description: ''
}
});
return (
<FormProvider {...methods}>
<RHFTextarea name="description" placeholder="Enter description" />
</FormProvider>
);
}Props API
Extends all props from Textarea component plus:
| Prop | Type | Default | Description |
|---|---|---|---|
name | string | - | Field name (required) |
control | Control | Auto-injected | Optional: Pass explicitly for nested forms or custom form context |
rules | RegisterOptions | - | Inline validation rules |
autoResize | boolean | false | Enable automatic height adjustment |
rows | number | 2 | Minimum number of rows |
maxRows | number | - | Maximum number of rows (only with autoResize) |
onChange | (value: string) => void | - | Change callback (receives value, not event) |
onBlur | (value: string) => void | - | Blur callback |
| ...rest | TextareaProps | - | All Textarea component props |
Examples
With Validation (Zod)
import { useForm, FormProvider } from 'react-hook-form';
import { zodResolver } from '@hookform/resolvers/zod';
import { z } from 'zod';
import { RHFTextarea, RHFInputGroup } from '@geckoui/geckoui';
const schema = z.object({
bio: z.string().min(10, 'Bio must be at least 10 characters').max(500, 'Bio must not exceed 500 characters')
});
function Example() {
const methods = useForm({
resolver: zodResolver(schema),
mode: 'onBlur',
defaultValues: { bio: '' }
});
return (
<FormProvider {...methods}>
<RHFInputGroup label="Bio" required>
<RHFTextarea name="bio" placeholder="Tell us about yourself (min 10 chars)" />
</RHFInputGroup>
</FormProvider>
);
}Auto-Resizing Textarea
<RHFTextarea
name="comments"
autoResize
rows={3}
maxRows={10}
placeholder="This textarea grows as you type (max 10 rows)"
/>With Row Constraints
<RHFTextarea
name="notes"
rows={5}
placeholder="Fixed at 5 rows"
/>Disabled State
<RHFTextarea name="readonly" disabled />Complete Form Example
import { useForm, FormProvider } from 'react-hook-form';
import { zodResolver } from '@hookform/resolvers/zod';
import { z } from 'zod';
import { RHFTextarea, RHFInputGroup, Button } from '@geckoui/geckoui';
const schema = z.object({
title: z.string().min(1, 'Title is required'),
description: z.string().min(20, 'Description must be at least 20 characters'),
notes: z.string().optional()
});
function FormExample() {
const methods = useForm({
resolver: zodResolver(schema),
mode: 'onBlur',
defaultValues: {
title: '',
description: '',
notes: ''
}
});
return (
<FormProvider {...methods}>
<form onSubmit={methods.handleSubmit(console.log)}>
<RHFInputGroup label="Title" required>
<RHFTextarea name="title" rows={1} placeholder="Enter title" />
</RHFInputGroup>
<RHFInputGroup label="Description" required>
<RHFTextarea
name="description"
autoResize
rows={3}
maxRows={8}
placeholder="Enter description (min 20 chars)"
/>
</RHFInputGroup>
<RHFInputGroup label="Additional Notes">
<RHFTextarea name="notes" rows={2} placeholder="Optional notes" />
</RHFInputGroup>
<Button type="submit">Submit</Button>
</form>
</FormProvider>
);
}Inline Rules Validation
For simple validation, use the rules prop:
<RHFTextarea
name="description"
rules={{
required: 'Description is required',
minLength: { value: 10, message: 'Must be at least 10 characters' }
}}
/>For complex forms, we recommend using a schema resolver (Zod, Yup) instead.
Error States
RHFTextarea automatically displays error states with:
- Red border via
data-errorattribute on the root element whenfieldState.errorexists
.GeckoUIRHFTextarea[data-error] {
border-color: red;
}Use RHFInputGroup component for label + textarea + error layout:
<RHFInputGroup label="Description" required>
<RHFTextarea name="description" />
</RHFInputGroup>Or combine with RHFError component manually:
<RHFTextarea name="description" />
<RHFError name="description" />Tip: Use mode: 'onBlur' in useForm to validate on blur for better UX:
const methods = useForm({
resolver: zodResolver(schema),
mode: 'onBlur'
});Auto-Resize Behavior
When autoResize is enabled:
- Textarea grows automatically as content increases
- Minimum height is determined by the
rowsprop - Maximum height is determined by the
maxRowsprop - Shrinks back down when content is removed
When autoResize is disabled:
- Textarea has a fixed height based on
rows - Users can resize manually (if CSS allows)
- The
maxRowsprop is ignored
Accessibility
- Inherits all accessibility features from Textarea component
- Proper ARIA attributes for error states
- Keyboard navigable
- Screen reader compatible