TextField

A text input component with label, description, and error handling for collecting user input.

Import

import { TextField } from 'heroui-native';

Anatomy

<TextField>
  <TextField.Label>...</TextField.Label>
  <TextField.Input>
    <TextField.InputStartContent>...</TextField.InputStartContent>
    <TextField.InputEndContent>...</TextField.InputEndContent>
  </TextField.Input>
  <TextField.Description>...</TextField.Description>
  <TextField.ErrorMessage>...</TextField.ErrorMessage>
</TextField>
  • TextField: Root container that provides spacing and state management
  • TextField.Label: Label with optional asterisk for required fields
  • TextField.Input: Input container with animated border and background
  • TextField.InputStartContent: Optional content at the start of the input
  • TextField.InputEndContent: Optional content at the end of the input
  • TextField.Description: Helper text displayed below the input
  • TextField.ErrorMessage: Error message shown when field is invalid

Usage

Basic Usage

TextField provides a complete form input structure with label and description.

<TextField>
  <TextField.Label>Email</TextField.Label>
  <TextField.Input placeholder="Enter your email" />
  <TextField.Description>We'll never share your email</TextField.Description>
</TextField>

With Required Field

Mark fields as required to show an asterisk in the label.

<TextField isRequired>
  <TextField.Label>Username</TextField.Label>
  <TextField.Input placeholder="Choose a username" />
</TextField>

With Start and End Content

Add icons or other content at the beginning or end of the input.

<TextField>
  <TextField.Label>Password</TextField.Label>
  <TextField.Input placeholder="Enter password" secureTextEntry>
    <TextField.InputStartContent>...</TextField.InputStartContent>
    <TextField.InputEndContent>...</TextField.InputEndContent>
  </TextField.Input>
</TextField>

With Validation

Display error messages when the field is invalid.

<TextField isRequired isInvalid={true}>
  <TextField.Label>Email</TextField.Label>
  <TextField.Input placeholder="Enter your email" />
  <TextField.ErrorMessage>Please enter a valid email</TextField.ErrorMessage>
</TextField>

With Local Invalid State Override

Override the context's invalid state for individual components.

<TextField isInvalid={true}>
  <TextField.Label isInvalid={false}>Email</TextField.Label>
  <TextField.Input placeholder="Enter your email" isInvalid={false} />
  <TextField.Description>
    This shows despite input being invalid
  </TextField.Description>
  <TextField.ErrorMessage>Email format is incorrect</TextField.ErrorMessage>
</TextField>

Multiline Input

Create text areas for longer content.

<TextField>
  <TextField.Label>Message</TextField.Label>
  <TextField.Input
    placeholder="Type your message..."
    multiline
    numberOfLines={4}
  />
  <TextField.Description>Maximum 500 characters</TextField.Description>
</TextField>

Disabled State

Disable the entire field to prevent interaction.

<TextField isDisabled>
  <TextField.Label>Disabled Field</TextField.Label>
  <TextField.Input placeholder="Cannot edit" value="Read only value" />
</TextField>

Custom Colors

Customize the input colors for different states using the animation prop.

<TextField>
  <TextField.Label>Custom Styled</TextField.Label>
  <TextField.Input
    placeholder="Custom colors"
    animation={{
      backgroundColor: {
        value: {
          blur: '#eff6ff',
          focus: '#dbeafe',
          error: '#eff6ff',
        },
      },
      borderColor: {
        value: {
          blur: '#2563eb',
          focus: '#1d4ed8',
          error: '#dc2626',
        },
      },
    }}
  />
</TextField>

Example

import { Ionicons } from '@expo/vector-icons';
import { TextField, useThemeColor } from 'heroui-native';
import React from 'react';
import { ScrollView, View } from 'react-native';

export default function TextFieldExample() {
  const themeColorMuted = useThemeColor('muted');
  const [email, setEmail] = React.useState('');
  const isInvalidEmail =
    email !== '' && !/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email);

  return (
    <ScrollView className="bg-background p-6">
      <View className="gap-6">
        <TextField isRequired isInvalid={isInvalidEmail}>
          <TextField.Label>Email Address</TextField.Label>
          <TextField.Input
            placeholder="Enter your email"
            keyboardType="email-address"
            autoCapitalize="none"
            value={email}
            onChangeText={setEmail}
          >
            <TextField.InputStartContent>
              <Ionicons name="mail-outline" size={16} color={themeColorMuted} />
            </TextField.InputStartContent>
          </TextField.Input>
          <TextField.Description>
            We'll send a confirmation to this email
          </TextField.Description>
          <TextField.ErrorMessage>
            Please enter a valid email address
          </TextField.ErrorMessage>
        </TextField>

        <TextField isRequired>
          <TextField.Label>Password</TextField.Label>
          <TextField.Input placeholder="Enter password" secureTextEntry>
            <TextField.InputStartContent>
              <Ionicons
                name="lock-closed-outline"
                size={16}
                color={themeColorMuted}
              />
            </TextField.InputStartContent>
            <TextField.InputEndContent>
              <Ionicons name="eye-outline" size={16} color={themeColorMuted} />
            </TextField.InputEndContent>
          </TextField.Input>
        </TextField>

        <TextField>
          <TextField.Label>Bio</TextField.Label>
          <TextField.Input
            placeholder="Tell us about yourself..."
            multiline
            numberOfLines={4}
          />
          <TextField.Description>
            Brief description for your profile
          </TextField.Description>
        </TextField>
      </View>
    </ScrollView>
  );
}

API Reference

TextField

proptypedefaultdescription
childrenReact.ReactNode-Content to render inside the text field
isDisabledbooleanfalseWhether the entire text field is disabled
isInvalidbooleanfalseWhether the text field is in an invalid state
isRequiredbooleanfalseWhether the text field is required (shows asterisk)
classNamestring-Custom class name for the root element
animation"disable-all" | undefinedundefinedAnimation configuration. Use "disable-all" to disable all animations including children
...ViewPropsViewProps-All standard React Native View props are supported

TextField.Label

proptypedefaultdescription
childrenReact.ReactNode-Label text content
isInvalidbooleanundefinedWhether the label is in an invalid state (overrides context)
classNamestring-Custom class name for the label element
classNamesElementSlots<LabelSlots>-Custom class names for different parts of the label
animationTextFieldLabelAnimation-Animation configuration
...Animated.TextPropsAnimatedProps<TextProps>-All Reanimated Animated.Text props are supported

ElementSlots<LabelSlots>

proptypedescription
textstringCustom class name for the label text
asteriskstringCustom class name for the asterisk

TextFieldLabelAnimation

Animation configuration for TextField.Label component. Can be:

  • false or "disabled": Disable all animations
  • true or undefined: Use default animations
  • object: Custom animation configuration
proptypedefaultdescription
entering.valueEntryOrExitLayoutTypeFadeIn
.duration(150)
.easing(Easing.out(Easing.ease))
Custom entering animation
exiting.valueEntryOrExitLayoutTypeFadeOut
.duration(150)
.easing(Easing.out(Easing.ease))
Custom exiting animation

TextField.Input

proptypedefaultdescription
childrenReact.ReactNode-Content to render inside the input container
isInvalidbooleanundefinedWhether the input is in an invalid state (overrides context)
classNamestring-Custom class name for the input container
classNamesElementSlots<InputSlots>-Custom class names for different parts of the input
animationTextFieldInputAnimation-Animation configuration
...TextInputPropsTextInputProps-All standard React Native TextInput props are supported

ElementSlots<InputSlots>

proptypedescription
containerstringCustom class name for the input container
inputstringCustom class name for the text input element

TextFieldInputAnimation

Animation configuration for TextField.Input component. Can be:

  • false or "disabled": Disable all animations
  • true or undefined: Use default animations
  • object: Custom animation configuration
proptypedefaultdescription
backgroundColor
.value
.blur
stringUses theme colorBackground color when input is blurred
backgroundColor
.value
.focus
stringUses theme colorBackground color when input is focused
backgroundColor
.value
.error
stringUses theme colorBackground color when input is invalid
backgroundColor
.timingConfig
WithTimingConfig{ duration: 150, easing: Easing.out(Easing.ease) }Animation timing configuration for background color transitions
borderColor
.value
.blur
stringUses theme colorBorder color when input is blurred
borderColor
.value
.focus
stringUses theme colorBorder color when input is focused
borderColor
.value
.error
stringUses theme colorBorder color when input is invalid
borderColor
.timingConfig
WithTimingConfig{ duration: 150, easing: Easing.out(Easing.ease) }Animation timing configuration for border color transitions

TextField.InputStartContent

proptypedefaultdescription
childrenReact.ReactNode-Content to render at the start of the input
classNamestring-Custom class name for the start content element
...ViewPropsViewProps-All standard React Native View props are supported

TextField.InputEndContent

proptypedefaultdescription
childrenReact.ReactNode-Content to render at the end of the input
classNamestring-Custom class name for the end content element
...ViewPropsViewProps-All standard React Native View props are supported

TextField.Description

proptypedefaultdescription
childrenReact.ReactNode-Description text content
isInvalidbooleanundefinedWhether the description is in an invalid state (overrides context)
classNamestring-Custom class name for the description element
animationTextFieldDescriptionAnimation-Animation configuration
...Animated.TextPropsAnimatedProps<TextProps>-All Reanimated Animated.Text props are supported

TextFieldDescriptionAnimation

Animation configuration for TextField.Description component. Can be:

  • false or "disabled": Disable all animations
  • true or undefined: Use default animations
  • object: Custom animation configuration
proptypedefaultdescription
entering.valueEntryOrExitLayoutTypeFadeIn
.duration(150)
.easing(Easing.out(Easing.ease))
Custom entering animation
exiting.valueEntryOrExitLayoutTypeFadeOut
.duration(150)
.easing(Easing.out(Easing.ease))
Custom exiting animation

TextField.ErrorMessage

Note: TextField.ErrorMessage extends ErrorView component. For complete API reference, see ErrorView documentation.

Hooks

useTextField

Hook to access the TextField context values. Must be used within a TextField component.

import { TextField, useTextField } from 'heroui-native';

function CustomComponent() {
  const { isDisabled, isInvalid, isRequired } = useTextField();

  // Use the context values...
}

Returns

propertytypedescription
isDisabledbooleanWhether the entire text field is disabled
isInvalidbooleanWhether the text field is in an invalid state
isRequiredbooleanWhether the text field is required

On this page