Text Input
Text inputs allow users to edit and input data. They can range from simple search boxes to long-form text areas.
# Anatomy
# Variants
# Default
This default serves as the basis for our Text Inputs. A shown here, they required paired with a paired Label.
# Search
Standalone Search provides minimal UI for searching outside of normal form contexts. Search inputs will render with the "Search" UI indicator as well as a visually hidden label.
In this case, we recommend using the placeholder attribute to state the scope of your search. This text should match the hidden label.
# Button variant
We also provide an attached button for in-page searching or avoiding placeholder text. Please follow our Button guidelines when using these variants.
# Textarea
Textareas should be used for multi-line text inputs. As the user types the field will grow vertically to accommodate the new lines.
# States
Text inputs support the following states: enabled, hover, focus, disabled, read-only, optional, and invalid.
# Enabled
Text inputs in their "normal" state are considered enabled. They are ready for user interaction.
# Hover
Hover states are activated when the user pauses their pointer over the input.
# Focus
The focus state is a visual affordance that the user has highlighted the input with a pointer, keyboard, or voice.
# Disabled
Disabled inputs are unavailable for interaction and cannot be focused. They can be used when input is disallowed, possibly due to a system state or access restrictions.
The values of disabled inputs will not be submitted.
# Read-only
Similar to disabled inputs, users cannot modify the values of read-only inputs. However, users can otherwise interact with read-only inputs and select their values for copying.
This state can be helpful when displaying computed or third-party values, or when a submitted form is being processed.
The values of read-only inputs will be submitted.
# Optional
Odyssey assumes inputs are required by default. Optional inputs should be used to indicate when data is not required for the user to complete a task.
# Invalid
The invalid state is for inputs with incorrect values or values of the wrong format.
When indicating a validation error, please use a Field Error label to indicate the nature of the error. Color alone is not an accessible way to signify that something has gone wrong.
# Content Guidelines
Text inputs support most free-form content, but we offer specific support for email, telephone numbers, and passwords.
There are no specific UI changes for email addresses, but inputs of this type will validate that the address is properly formatted.
# Tel
Unlike email fields, tel inputs are not automatically validated because global formats are so varied.
# Password
Passwords inputs ensure that sensitive content is safely obscured.
# Accessibility
# Placeholders
Except for Search inputs, we advise against using placeholder text for inputs.
# Translation
To prevent triggering a change in page layout, browsers don't translate certain attributes. Because of this, users will see untranslated placeholder text.
# Recall
Placeholder text disappears when a field is interacted with. For this reason, it's not suitable for formatting guidelines or necessary context.
# Utility
Placeholder content is limited to static text. Additionally, placeholder text is truncated beyond the width of its input.
# Field value confusion
Low-contrast placeholders may be illegible for some users. Yet, placeholders with compliant contrast can be mistaken for field values. High Contrast Mode will make placeholders and values appear identical.
Finally, Users with low digital literacy may not understand the purpose or behavior of placeholder text.
# Types
Out of the box, Odyssey supports input types for text, email, search, tel, and password with more coming soon.
# Text
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<input class="ods-text-input" type="text" name="example-1" id="example-1" spellcheck="false" value="Input value" required>
<label class="ods-label" for="example-1">Field label</label>
</div>
</fieldset>
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<input class="ods-text-input" type="email" name="example-2" id="example-2" autocomplete="email" spellcheck="false" value="name@okta.design" required>
<label class="ods-label" for="example-2">Email</label>
</div>
</fieldset>
# Telephone
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<input class="ods-text-input" type="tel" name="example-3" id="example-3" spellcheck="false" value="888-722-7871" required>
<label class="ods-label" for="example-2">Telephone number</label>
</div>
</fieldset>
# Password
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<input class="ods-text-input" type="password" name="example-4" id="example-4" spellcheck="false" value="fake-password-value" required>
<label class="ods-label" for="example-4">Password</label>
</div>
</fieldset>
# Search
<fieldset class="ods-fieldset">
<input type="search" name="example-5" id="example-5" autocomplete="search" placeholder="Placeholder value" spellcheck="false" aria-labelledby="example-5" required="required" class="ods-text-input">
</fieldset>
# Search with attached primary button
<fieldset class="ods-fieldset">
<div class="ods-fieldset--attached">
<input type="search" name="example-6" id="example-6" autocomplete="search" spellcheck="false" aria-labelledby="example-6" required="required" class="ods-text-input">
<button id="example-6" class="ods-button">Button label</button>
</div>
</fieldset>
# Search with attached secondary button
<fieldset class="ods-fieldset">
<div class="ods-fieldset--attached">
<input type="search" name="example-7" id="example-7" autocomplete="search" spellcheck="false" aria-labelledby="example-7" required="required" class="ods-text-input">
<button id="example-7" class="ods-button is-ods-button-secondary">Button label</button>
</div>
</fieldset>
# Textarea
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<textarea class="ods-text-input ods-text-area" name="example-8" id="example-8" rows='4' cols='50' spellcheck="true" required></textarea>
<aside class="ods-field--hint">
Descriptive field hint
</aside>
<label class="ods-label" for="example-8">Field label</label>
</div>
</fieldset>
# States
# Disabled
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<input class="ods-text-input" type="text" name="example-9" id="example-9" spellcheck="false" value="Disabled input value" disabled required>
<label class="ods-label" for="example-9">Field label</label>
</div>
</fieldset>
# Optional label
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<input class="ods-text-input" type="text" name="example-10" id="example-10" spellcheck="false" value="">
<label class="ods-label" for="example-10">Field label <span class="ods-label--optional">Optional</span></label>
</div>
</fieldset>
# Invalid label
Because of the current inability to ensure consistent validation behavior across browsers, we're using the [data-invalid] attribute to indicate this state.
<fieldset class="ods-fieldset">
<div class="ods-fieldset-flex">
<input class="ods-text-input" type="text" name="example-11" id="example-11" spellcheck="false" value="" data-invalid required>
<label class="ods-label" for="example-11">Field label</label>
<aside class="ods-field--error" id="overview-invalid-error">
<span class="u-visually-hidden">Error:</span> Invalid error description
</aside>
</div>
</fieldset>