Skip to content
SuperCoach

Components · Inputs

Textarea

Beta

A multi-line field, such as coach notes on a check-in.

Sara sees this with her week 4 check-in.

When to use

  • For free text that may run to several lines: check-in feedback, coach notes, a program description, a message to clients.

When not to use

  • For a short single value (a name, a weight, a code): use an Input.
  • For formatted content with headings, lists or links: use a rich-text editor.
  • For a chat-style composer with send on Enter: that is a pattern built on a textarea, with its own keyboard rules.

Anatomy

Only you and other coaches see notes.

  1. 1. Label: always visible, linked with htmlFor
  2. 2. Field: grows with its content from a 64px minimum
  3. 3. Help text or counter (optional): linked with aria-describedby

Variants

Characters left: 280

VariantUse for
Auto-growing (default)Most fields. field-sizing-content grows the field as people type, so nothing scrolls inside it. Set max-h-* if it sits in a small panel.
Fixed height, with counterWhen the text has a hard limit (an SMS, a push message). Add field-sizing-fixed, rows, maxLength and a counter linked with aria-describedby.

States

Add a reason so the client knows why.

StateWhat changesToken
PlaceholderMuted textplaceholder:text-muted-foreground
Focus-visibleBorder and ringborder-ring, ring-ring/50, 3px
DisabledHalf opacity, not-allowed cursor. Dim the label too (see Label)opacity-(--opacity-disabled)
Invalid (aria-invalid)Red border and ring, error text belowborder-destructive, ring-destructive/20, text-destructive-text

Usage guidelines

Do.A visible label above the field, and the field sized for the text it expects.
Don't.The placeholder as the only label. It disappears as soon as someone types, so they lose the question while answering it.
  • Use the placeholder for an example of good content ("What went well this week…"), not for instructions people need while typing. Put those in help text.
  • Show a counter only when there is a limit, and say what's left: "Characters left: 120".
  • Don't block line breaks or submit on Enter in a form field; people expect Enter to add a new line.

Content guidelines

  • Labels are nouns: "Check-in feedback", "Program description". Sentence case, no colon.
  • Help text says who sees the text or what it is for: "Sara sees this with her week 4 check-in."
  • Error messages say how to fix it: "Add a reason so the client knows why."
  • Arabic text in a textarea follows the field's direction. Mixed Arabic and English (exercise names) is handled by the browser; set dir="auto" on fields where clients may write in either language.

Accessibility

KeyDoes
TabMoves focus to the field
EnterAdds a new line
Shift+TabLeaves the field backward
  • Renders a native <textarea>, linked to its label with htmlFor/id. Announced as "Check-in feedback, edit text, multi-line", followed by the help text.
  • Errors: set aria-invalid="true" and link the message with aria-describedby, so it is read with the label.
  • A counter linked with aria-describedby is read on focus. Don't make it a live region; it would speak on every key press.
  • Use useId() for the ids, so two fields on one screen never share one.

RTL

  • The text, placeholder and caret follow the page direction; help text and errors align to the start.
  • The resize handle stays in the bottom corner on the end side (bottom-left in RTL), drawn by the browser.
  • The counter in the example uses text-end, so it sits at the left in RTL.

Tokens used

Read from components/ui/textarea.tsx at build time, so this list changes when the component does. Opacity modifiers such as /90 are shadcn hover and focus tints on top of the token.

Semantic color tokens used by this component
TokenUtilitiesSuperCoachCoach
--destructiveborder-destructive ring-destructive/20red-600red-600
--inputborder-inputneutral-200neutral-200
--muted-foregroundtext-muted-foregroundneutral-600neutral-600
--ringborder-ring ring-ring/50brand-600orange-500
  • Opacityopacity-(--opacity-disabled)
  • Radiusrounded-md
  • Shadowshadow-xs
  • Typetext-base
  • Typetext-sm

Props

<Textarea>

Also takes every prop of <textarea>

No props of its own.

Replaces in coach-admin

From the read-only audit of coach-admin: 46 style values, 48 uses.

coach-admin has a shared formComponents/textarea, but most screens style their own (.faq-textarea, .quick-message-modal__textarea, .post-textarea, .textArea-style). All become this component, with the counter pattern above replacing .textarea-widget__counter.

Classes and selectors

  • textarea7
  • .faq-textarea6
  • .quick-message-modal__textarea5
  • &.textArea-style4
  • .supercoach-ai__footer-textarea-container3
  • .post-textarea3
  • .textarea-widget__counter3
  • .editInputStyle-textarea-no-value2
  • .el-textarea2
  • .challenge-settings-section__terms-textarea2
  • .verification-queue-modal__textarea2
  • input, select, textarea1

Files

  • src/reusableComponents/formComponents/textarea/textarea.scss7

The inventory lists the first 12 locations of each value, so file counts are a lower bound.

SCSS variables in these styles

  • $ai-light-gray-bg→ nearest neutral-50 (no semantic token)

Input, Label, Form.