Textarea
A multi-line text field that can grow with its content.
import '@usezeno/tokens/css';
import '@usezeno/core/web-components';
Examples
Basic
The label attribute renders a label above the field. rows sets the height in lines.
<zeno-textarea label="Notes" placeholder="Add a note for your team" rows="4"></zeno-textarea>
Sizes and variants
<zeno-textarea size="sm" label="Small" value="Small text"></zeno-textarea>
<zeno-textarea size="md" label="Medium" value="Medium text"></zeno-textarea>
<zeno-textarea size="lg" label="Large" value="Large text"></zeno-textarea>
<zeno-textarea variant="outlined" label="Outlined" value="The default variant"></zeno-textarea>
<zeno-textarea variant="filled" label="Filled" value="A filled background"></zeno-textarea>
Auto resize, counter and clear button
With auto-resize the field grows with its text. maxlength limits the text and shows a counter. show-count shows a counter with no limit. With clearable, a clear button shows when the pointer is over the field or the field has focus.
<zeno-textarea label="Grows with the text" auto-resize rows="2" value="Type a few lines here."></zeno-textarea>
<zeno-textarea label="Short description" maxlength="80" value="A weekly report for the sales team."></zeno-textarea>
<zeno-textarea label="Comment" show-count clearable resize="none" value="Looks good to me."></zeno-textarea>
States
The error text shows below the field. success and loading only change how the field looks.
<zeno-textarea label="Disabled" value="You cannot change this text." disabled></zeno-textarea>
<zeno-textarea label="Read only" value="You can select this text but not change it." readonly></zeno-textarea>
<zeno-textarea label="With an error" value="Too short" error="Write at least 20 characters."></zeno-textarea>
<zeno-textarea label="Success" value="This description is long enough." success></zeno-textarea>
<zeno-textarea label="Loading" loading></zeno-textarea>
In a form
The value is sent under name. Submit the empty form to see the message for a required field.
<form>
<zeno-textarea name="message" label="Message" rows="3" required></zeno-textarea>
<zeno-button type="submit">Send</zeno-button>
<zeno-button type="reset" variant="ghost">Reset</zeno-button>
<p data-result>Nothing submitted yet.</p>
</form>
const form = document.querySelector('form');
form.addEventListener('submit', event => {
event.preventDefault();
const sent = [...new FormData(form)].map(([name, value]) => name + '=' + value);
document.querySelector('[data-result]').textContent = 'Submitted: ' + sent.join('&');
});
Attributes and properties
| Property | Attribute | Type | Default | Description |
|---|---|---|---|---|
variant | variantreflects | 'outlined' | 'filled' | 'underlined' | 'outlined' | |
size | sizereflects | 'sm' | 'md' | 'lg' | 'md' | |
placeholder | placeholder | string | ||
rows | rows | number | 3 | |
minlength | minlength | number | ||
maxlength | maxlength | number | ||
resize | resizereflects | 'none' | 'vertical' | 'horizontal' | 'both' | 'vertical' | |
autoResize | auto-resizereflects | boolean | false | |
autofocus | autofocusreflects | boolean | false | |
clearable | clearablereflects | boolean | false | |
loading | loadingreflects | boolean | false | |
success | successreflects | boolean | false | |
showCount | show-countreflects | boolean | false | |
value | value | FormValue | '' | From FormFieldMixin. |
name | namereflects | string | From FormFieldMixin. | |
required | requiredreflects | boolean | false | From FormFieldMixin. |
disabled | disabledreflects | boolean | false | From FormFieldMixin. |
readonly | readonlyreflects | boolean | false | From FormFieldMixin. |
error | error | string | An error to show, for example one a server returned. From FormFieldMixin. | |
label | label | string | A visible label. An outside <label for> works as well. From FormFieldMixin. | |
hideRequiredIndicator | hide-required-indicator | boolean | false | From FormFieldMixin. |
touched | boolean | false | True once the user has left the control or a submit was refused. From FormFieldMixin. | |
dirty | boolean | false | True once the user has changed the value. From FormFieldMixin. | |
defaultValue | FormValue | '' | The value the control goes back to when its form is reset. From FormFieldMixin. | |
formread only | HTMLFormElement | null | From FormFieldMixin. | ||
labelsread only | NodeList | From FormFieldMixin. | ||
validityread only | ValidityState | From FormFieldMixin. | ||
validationMessageread only | string | From FormFieldMixin. | ||
willValidateread only | boolean | From FormFieldMixin. | ||
isDisabledread only | boolean | True when the element or an ancestor fieldset disables it. From FormFieldMixin. | ||
invalidread only | boolean | True when the control should look invalid. From FormFieldMixin. | ||
testId | string | Test ID for automated testing From ZenoElement. |
Methods
| Method | Description |
|---|---|
focus(options?: FocusOptions): void | Focus the textarea element From ZenoElement. |
blur(): void | Blur the textarea element From ZenoElement. |
select(): void | Select all text in the textarea |
setSelectionRange(start: number, end: number, direction?: 'forward' | 'backward' | 'none'): void | Set selection range |
checkValidity(): boolean | Reports whether the value is valid without showing anything. Use reportValidity() or validate() to show the result as well. From FormFieldMixin. |
reportValidity(): boolean | From FormFieldMixin. |
setCustomValidity(message: string): void | From FormFieldMixin. |
validate(): boolean | Checks validity and shows the result on the control. From FormFieldMixin. |
Events
| Event | Detail | Description |
|---|---|---|
input | { value: FormValue } | The value changed while typing. |
change | { value: FormValue } | The value was committed. |
clear | The clear button was pressed. |
Slots
This element has no slots.
CSS parts
| Part |
|---|
clear-button |
count |
error |
footer |
label |
loading |
textarea |
wrapper |
CSS custom properties
This element documents no custom properties of its own. Style it through its parts and through the tokens it reads.
The element's own source reads no tokens.
Types
type FormValue = string | number | boolean | Date | null | undefined;
Accessibility
Keyboard
| Key | What it does |
|---|---|
| Tab | Moves focus to the text field. |
| Enter | Adds a new line. It does not submit the form. |
Forms
- With a
name, the element adds its value to the data of the form it is in, and is left out while it is disabled. - It is labelled by its
labelattribute or by a<label for>that points at itsid. - It takes part in validation:
checkValidity(),reportValidity()andsetCustomValidity()work, and an invalid element blocks the submit and matches:invalid. - It follows a
<fieldset disabled>around it and goes back to its first value when the form is reset. - The messages it writes itself, such as “Please fill out this field.”, are in English only.
Notes
- The control is a native
<textarea>. Typing, selection and the keys come from it. - The
labelattribute renders a<label>for the field. Without it, the name comes from an outside<label for>or fromaria-labelon the element. - A required field shows
*after the label. The mark is hidden from assistive technology, and the nativerequiredattribute is set on the field. - When the field is invalid, it has
aria-invalid="true"andaria-describedbypoints at the error text. disabledandreadonlyset the native attributes with the same names on the field.
Tests and known gaps
- Tested in a real browser by
textarea.test.ts. - Checked with axe-core in the light and the dark theme.
- Has no Storybook story.
34 of the 51 properties, methods, events, slots and parts above have no description in the source
- the property
variant - the property
size - the property
placeholder - the property
rows - the property
minlength - the property
maxlength - the property
resize - the property
autoResize - the property
autofocus - the property
clearable - the property
loading - the property
success - the property
showCount - the property
value - the property
name - the property
required - the property
disabled - the property
readonly - the property
hideRequiredIndicator - the property
form - the property
labels - the property
validity - the property
validationMessage - the property
willValidate - the method
reportValidity() - the method
setCustomValidity() - the part
clear-button - the part
count - the part
error - the part
footer - the part
label - the part
loading - the part
textarea - the part
wrapper
Known gaps:
- The
varianttype listsunderlined, but the element has no styles for it. The element has styles forghost, which the type does not list. - The clear button has
tabindex="-1", so it cannot be reached with the keyboard. - The clear button label is the fixed English text “Clear textarea”. No attribute changes it.
- While
loading, the text is made transparent but the field can still be edited. The field has noaria-busy. - The
successstate is shown by the border colour only. No text or icon says that the value is good. - The character counter is not linked to the field and is not a live region, so assistive technology does not read it.
- The counter shows whenever
maxlengthis set. It cannot be turned off for a field with a limit.