{ "$schema": "https://ui.shadcn.com/schema/registry-item.json", "name": "textarea", "type": "registry:ui", "title": "Textarea", "description": "Multiline TextInput.", "registryDependencies": [ "https://raw.githubusercontent.com/truongnat/rnui/main/registry/dist/nativewind/utils.json", "https://raw.githubusercontent.com/truongnat/rnui/main/registry/dist/nativewind/theme.json" ], "files": [ { "path": "registry/shared/ui/textarea.tsx", "type": "registry:ui", "target": "components/ui/textarea.tsx", "content": "import { forwardRef, useContext, useState } from 'react';\nimport { StyleSheet, TextInput, type TextInputProps, type TextStyle } from 'react-native';\nimport { cn, FormFieldContext, useThemeColor } from '@/lib/utils';\n\nexport interface TextareaProps extends TextInputProps {\n className?: string;\n placeholderClassName?: string;\n /**\n * Mirrors shadcn `aria-invalid` — renders a destructive border.\n * Auto-detected from when inside one.\n */\n invalid?: boolean;\n /** Alias for `editable={false}` plus disabled styling. */\n disabled?: boolean;\n}\n\nexport const Textarea = forwardRef(\n (\n {\n className,\n placeholderClassName,\n invalid,\n disabled,\n editable,\n multiline = true,\n onFocus,\n onBlur,\n selectionColor,\n cursorColor,\n nativeID,\n style,\n ...props\n },\n ref\n ) => {\n const [focused, setFocused] = useState(false);\n const field = useContext(FormFieldContext);\n const colors = useThemeColor();\n const isInvalid = invalid ?? !!field?.error;\n const isDisabled = disabled || editable === false;\n\n const placeholder = cn('text-muted-foreground/60', placeholderClassName);\n const placeholderProps = {\n placeholderClassName: placeholder,\n placeholderTextColorClassName: placeholder,\n };\n\n const dynamicStyle: TextStyle = {\n borderColor: isInvalid\n ? colors.destructive\n : focused\n ? colors.ring || colors.primary\n : colors.input || colors.border,\n borderWidth: focused || isInvalid ? 1.5 : 1,\n backgroundColor: colors.background,\n };\n\n return (\n {\n setFocused(true);\n onFocus?.(e);\n }}\n onBlur={(e) => {\n setFocused(false);\n onBlur?.(e);\n }}\n {...(placeholderProps as Partial)}\n {...props}\n />\n );\n }\n);\nTextarea.displayName = 'Textarea';\n\nconst styles = StyleSheet.create({\n baseTextarea: {\n borderCurve: 'continuous',\n fontSize: 15,\n },\n});\n" } ] }