npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@dreamworld/dw-input

v4.1.28

Published

Material design styled input text-field & text-area implemented in LitElement

Downloads

2,439

Readme

@dreamworld/dw-input

A Material Design outlined text-field and auto-grow textarea library implemented as LitElement Web Components, providing full validation, tooltip messaging, value formatting hooks, and rich icon support.

Exports: <dw-input>, <dw-textarea>, <dw-email-input>


1. User Guide

Installation & Setup

yarn add @dreamworld/dw-input

This package is an ES module. Import each component as needed:

// Core input (Material Design outlined text field)
import '@dreamworld/dw-input/dw-input.js';

// Auto-grow undecorated textarea
import '@dreamworld/dw-input/dw-textarea.js';

// Email-specialized input
import '@dreamworld/dw-input/dw-email-input.js';

To extend the class directly:

import { DwInput } from '@dreamworld/dw-input/dw-input.js';
import { DwTextarea } from '@dreamworld/dw-input/dw-textarea.js';
import { DwEmailInput } from '@dreamworld/dw-input/dw-email-input.js';

Basic Usage

<!-- Simple labeled input -->
<dw-input label="Full Name" placeholder="Enter your name" required></dw-input>

<!-- Number input with bounds -->
<dw-input label="Age" type="number" .minNumber=${1} .maxNumber=${120}></dw-input>

<!-- Disabled input with pre-filled value -->
<dw-input label="Account ID" value="12345" disabled></dw-input>

<!-- Read-only input with icons -->
<dw-input label="Search" readOnly icon="search" iconTrailing="close"></dw-input>

<!-- Input with hint and validation -->
<dw-input
  label="Username"
  required
  hint="Letters and numbers only"
  pattern="[a-zA-Z0-9]+"
  error="Invalid characters"
></dw-input>

<!-- Multiline (textarea) mode -->
<dw-input label="Notes" multiline .minHeight=${80} .maxHeight=${200}></dw-input>

<!-- Auto-grow undecorated textarea -->
<dw-textarea .minHeight=${80} .maxHeight=${200} placeholder="Type here..."></dw-textarea>

<!-- Email input -->
<dw-email-input label="Email Address" required></dw-email-input>

API Reference — <dw-input>

Props

| Name | Type | Default | Required | Description | |------|------|---------|----------|-------------| | name | String | '' | No | The name attribute of the underlying input element | | value | String | '' | No | Current value of the input field | | type | String | 'text' | No | Input type (e.g. text, email, number, password) | | inputmode | String | undefined | No | HTML inputmode attribute (e.g. numeric, email) | | maxNumber | Number | undefined | No | Maximum value when type="number" | | minNumber | Number | undefined | No | Minimum value when type="number" | | step | Number | 'any' | No | Step interval for legal numbers when type="number" | | label | String | undefined | No | Floating label text | | placeholder | String | '' | No | Placeholder text shown inside the field | | disabled | Boolean | false | No | Disables the input | | readOnly | Boolean | false | No | Makes the input read-only | | required | Boolean | false | No | Marks input as required; validated on validate() | | pattern | String | '(.*?)' | No | Regex pattern validated during validate() | | allowedPattern | String | undefined | No | Regex pattern checked on each keystroke; disallows non-matching characters | | minLength | Number | 0 | No | Minimum number of characters | | maxLength | Number | 524288 | No | Maximum number of characters accepted | | charCounter | Boolean | false | No | Shows character counter; requires maxLength to be set | | hint | String | undefined | No | Helper text shown below the field (only while focused by default) | | hintPersistent | Boolean | false | No | Always show hint text regardless of focus state | | hintInTooltip | Boolean | false | No | Show hint in a tooltip triggered by a trailing info icon instead of below the field | | hintTooltipActions | Array | undefined | No | Array of tooltipAction objects shown as buttons inside the hint tooltip | | error | String\|Function\|Object | '' | No | Error message shown when invalid. Can be a string, or a Function(value) => string | | errorInTooltip | Boolean | false | No | Show error in a tooltip triggered by a trailing error icon | | errorTooltipActions | Array | undefined | No | Array of tooltipAction objects shown as buttons inside the error tooltip | | warning | String\|Function\|Object | undefined | No | Warning message. Can be a string or Function(value) => string | | warningInTooltip | Boolean | false | No | Show warning in a tooltip triggered by a trailing warning icon | | warningTooltipActions | Array | undefined | No | Array of tooltipAction objects shown as buttons inside the warning tooltip | | tipPlacement | String | 'bottom-end' | No | Tooltip placement; see Tippy.js placement docs | | tipExtraOptions | Object | undefined | No | Additional options passed directly to the Tippy.js tooltip instance | | icon | String | undefined | No | Leading (prefix) icon name | | iconTrailing | String | undefined | No | Trailing (suffix) icon name | | iconSize | Number | 24 | No | Size in px for both leading and trailing icons | | iconButtonSize | Number | 24 | No | Size in px for icon buttons (when clickableIcon=true) | | iconFont | String | undefined | No | Icon font variant: 'FILLED' or 'OUTLINED' | | symbol | Boolean | false | No | When true, uses Material Symbols icon set | | clickableIcon | Boolean | false | No | Makes the trailing icon interactive (rendered as icon button) | | autoSelect | Boolean | false | No | Auto-selects all text when the field receives focus | | multiline | Boolean | false | No | Renders the input as a textarea | | minHeight | Number | 42 | No | Minimum height in px when multiline=true | | maxHeight | Number | undefined | No | Maximum height in px when multiline=true; enables scroll beyond this | | disabledEnter | Boolean | false | No | Prevents newline insertion on Enter key when multiline=true | | dense | Boolean | false | No | Applies dense (compact) field style | | showAsFilled | Boolean | false | No | Renders field in Material Design filled style instead of outlined | | noHintWrap | Boolean | false | No | Forces hint text to render on a single line (no wrapping) | | prefixText | String | '' | No | Static prefix text rendered inside the field before the input | | suffixText | String | undefined | No | Static suffix text rendered inside the field after the input | | truncateOnBlur | Boolean | false | No | Trims whitespace from value when the field loses focus | | originalValue | String | undefined | No | Reference value used to detect changes when highlightChanged=true | | highlightChanged | Boolean | false | No | Highlights the field when value !== originalValue | | highlightedValue | Boolean | false | No | When true, displays value in highlighted style unconditionally | | valueEqualityChecker | Function | undefined | No | Custom equality function (val1, val2) => Boolean used by highlightChanged logic | | errorMessages | Object | (internal defaults) | No | Map of validity-key → error string overrides (e.g. { typeMismatch: '...' }) | | validity | Object | undefined | No | The ValidityState object of the underlying input element | | autocomplete | String | 'off' | No | Maps to the HTML autocomplete attribute |

Events

| Event | When Fired | detail | |-------|-----------|---------| | value-changed | When the user types and the value changes | { value: String } | | change | On blur after the user has modified the value | none | | enter | When the Enter key is pressed | { value: String, event: KeyboardEvent } | | esc | When the Escape key is pressed | { value: String, event: KeyboardEvent } | | show-password | When the user clicks the visibility icon to reveal password | none | | hide-password | When the user clicks the visibility icon to hide password | none | | action | When a tooltip action button is clicked | action name (String) |

Methods

| Method | Signature | Returns | Description | |--------|-----------|---------|-------------| | focus | focus() | void | Sets focus to the input | | setCaretPosition | setCaretPosition(caretPos: Number) | void | Moves caret to the specified character position | | selectText | selectText() | void | Selects all text in the input | | checkValidity | checkValidity() | Boolean | Runs validation; returns true if valid | | setCustomValidity | setCustomValidity(msg: String) | void | Sets a custom validity message (empty string clears it) | | reportValidity | reportValidity() | Boolean | Runs validation and reports result; returns true if valid | | validate | validate() | Boolean | Legacy alias for checkValidity(); returns false if invalid | | layout | layout() | void | Triggers MDC layout recalculation (use after dynamic show/hide) | | parseValue | parseValue(text: String) => String | String | Override in subclasses to parse raw input text into a structured value | | formatText | formatText(value: String) => String | String | Override in subclasses to format a structured value into display text | | showPassword | showPassword() | void | Switches type to 'text' to reveal password | | hidePassword | hidePassword() | void | Switches type back to 'password' | | DwInput.setErrorMessages (static) | DwInput.setErrorMessages(messages: Object) | void | Sets default error messages at the application level for all instances |

CSS Custom Properties

| Property | Default | Controls | |----------|---------|---------| | --dw-input-outlined-idle-border-color | rgba(0,0,0,0.38) | Outlined border color in idle state | | --dw-input-outlined-hover-border-color | rgba(0,0,0,0.87) | Outlined border color on hover | | --dw-input-outlined-disabled-border-color | rgba(0,0,0,0.06) | Outlined border color when disabled | | --dw-input-outlined-readonly-idle-border-color | — | Outlined border color when read-only | | --dw-input-text-field-color | var(--mdc-theme-text-primary, rgba(0,0,0,0.87)) | Input text color | | --dw-input-fill-color | whitesmoke | Background fill when showAsFilled=true | | --dw-input-filled-bottom-border-color | rgba(0,0,0,0.42) | Bottom border color for filled style | | --dw-input-filled-hover-bottom-border-color | rgba(0,0,0,0.87) | Hover bottom border color for filled style | | --dw-input-value-updated-color | var(--mdc-theme-primary, #02afcd) | Text color when value is changed (highlightChanged) | | --dw-input-outlined-updated-bg-color | var(--mdc-theme-primary, #02afcd) | Background overlay when value is changed | | --dw-input-helper-line-position | relative | CSS position of the hint/error helper line | | --dw-input-white-space | — | white-space property of input text when not focused | | --dw-input-text-overflow | — | text-overflow property when not focused | | --dw-input-overflow | — | overflow property when not focused | | --dw-input-direction | — | Text direction (ltr/rtl) when not focused | | --dw-input-text-align | — | Text alignment when not focused | | --dw-icon-color | rgba(0,0,0,0.54) | Icon color | | --dw-icon-color-disabled | rgba(0,0,0,0.38) | Icon color when disabled | | --mdc-theme-primary | rgba(98,0,238,0.87) | Material Design primary color (focus ring, active state) | | --mdc-theme-text-primary | rgba(0,0,0,0.87) | Primary text color | | --mdc-theme-text-secondary | rgba(0,0,0,0.6) | Secondary/label text color | | --mdc-theme-text-disabled | rgba(0,0,0,0.38) | Disabled text color | | --mdc-theme-error | #b00020 | Error state color | | --mdc-theme-text-warning | #ffa726 | Warning state color |


API Reference — <dw-textarea>

Props

| Name | Type | Default | Required | Description | |------|------|---------|----------|-------------| | value | String | '' | No | Current textarea value | | minHeight | Number | 42 | No | Minimum height in px; textarea auto-grows from this value | | maxHeight | Number | undefined | No | Maximum height in px; vertical scroll activates beyond this | | maxLength | Number | 524288 | No | Maximum number of characters | | minLength | Number | 0 | No | Minimum number of characters | | readOnly | Boolean | false | No | Makes the textarea read-only | | disabled | Boolean | false | No | Disables the textarea | | required | Boolean | false | No | Marks the textarea as required | | placeholder | String | '' | No | Placeholder text | | disabledEnter | Boolean | false | No | Prevents newline insertion on Enter key | | undecorated | Boolean | false | No | Hides the border when true | | showPlaceholderOnFocusOnly | Boolean | false | No | Hides placeholder until the element is focused | | autocomplete | String | 'off' | No | HTML autocomplete attribute |

Events

| Event | When Fired | detail | |-------|-----------|---------| | value-changed | When the value changes (user input or programmatic) | { value: String } | | change | On blur after value was modified by the user | none | | input | As the user types (mirrors native input event) | none | | enter | When Enter key is pressed | { value: String, event: KeyboardEvent } | | esc | When Escape key is pressed | { value: String, event: KeyboardEvent } | | blur | When the textarea loses focus | { value: String, event: FocusEvent } |

Methods

| Method | Signature | Returns | Description | |--------|-----------|---------|-------------| | focus | focus() | void | Sets focus and moves caret to end of text | | focusToEnd | focusToEnd() | void | Alias for focus() (backward compatibility) | | moveToEnd | moveToEnd() | void | Moves caret to end of text and resizes the textarea | | moveToStart | moveToStart() | void | Moves caret to start of text and resizes the textarea | | blur | blur() | void | Removes focus from the textarea | | validate | validate() | Boolean | Validates the textarea; returns false if invalid | | checkValidity | checkValidity() | Boolean | Checks validity; returns true if valid | | setCustomValidity | setCustomValidity(msg: String) | void | Sets a custom validity message (empty string clears it) | | validity (getter) | get validity() | ValidityState | Returns the ValidityState of the underlying <textarea> |

CSS Custom Properties

| Property | Default | Controls | |----------|---------|---------| | --dw-textarea-padding | 0px | Internal padding of the textarea | | --mdc-theme-text-primary | rgba(0,0,0,0.87) | Text color | | --mdc-theme-text-hint-on-background | rgba(0,0,0,0.38) | Placeholder/hint text color | | --mdc-theme-secondary | — | Focused border/outline color | | --divider-color | — | Border color |

Note: dw-textarea has no default border or background color. Apply border and background directly to the dw-textarea element at the usage site. Apply a typography class (e.g. from @dreamworld/material-styles) to control font styles — no default typography is applied.


API Reference — <dw-email-input>

<dw-email-input> extends <dw-input> with no additional props, events, or CSS variables. It differs only in its constructor defaults:

| Property | Value set in constructor | |----------|--------------------------| | type | 'email' | | errorMessages.typeMismatch | 'Invalid Email' |

All props, methods, events, and CSS custom properties from <dw-input> are inherited.

<dw-email-input label="Email Address" required></dw-email-input>

Configuration Options

Application-Level Error Messages

Override default error messages for all <dw-input> instances in your application:

import { DwInput } from '@dreamworld/dw-input/dw-input.js';

DwInput.setErrorMessages({
  valueMissing: 'This field is required.',
  typeMismatch: 'Please enter a valid value.',
  patternMismatch: 'The format is incorrect.',
  tooShort: 'Too short.',
  tooLong: 'Too long.',
  rangeUnderflow: 'Value is too low.',
  rangeOverflow: 'Value is too high.',
});

Tooltip Action Object Shape

Used with hintTooltipActions, errorTooltipActions, and warningTooltipActions:

{
  name: String,    // Identifier emitted with the `action` event
  label: String,   // Button label displayed in the tooltip
  danger: Boolean  // When true, renders the button in a danger/destructive style
}

Advanced Usage

Value Parsing & Text Formatting

Override parseValue and formatText in a subclass to decouple the internal value from the displayed text. This enables custom input formats (e.g. locale-formatted numbers, date inputs).

  • formatText(value) — receives value (the structured property value), returns the string to display in the text field.
  • parseValue(text, userEditing) — receives the raw input text and a Boolean indicating whether the user is still editing. Returns the parsed value to assign to value.
    • Returning undefined during userEditing=true leaves value unchanged, enabling intermediate invalid state handling.
    • Returning any value (including undefined) on blur (userEditing=false) sets value.

Example — locale-formatted number input:

import { DwInput } from '@dreamworld/dw-input/dw-input.js';

class FormattedInput extends DwInput {
  formatText(value) {
    value = value.toString().replace(/,/g, '').replace(/ /g, '');
    return Number(value).toLocaleString();
  }

  parseValue(text) {
    text = text.replace(/,/g, '').replace(/ /g, '');
    return Number(text);
  }
}

customElements.define('formatted-input', FormattedInput);
<formatted-input label="Amount" value="1000000"></formatted-input>
<!-- Displays: 1,000,000 -->

Custom Styling via Subclass

import { DwInput } from '@dreamworld/dw-input/dw-input.js';
import { css } from 'lit';

class RoundedInput extends DwInput {
  static get styles() {
    return [
      DwInput.styles,
      css`
        .mdc-text-field {
          border-radius: 8px;
        }
      `
    ];
  }
}

customElements.define('rounded-input', RoundedInput);

Highlight Changed Value

Highlight a field when its current value differs from a reference value — useful in edit forms:

<dw-input
  label="Username"
  value="john_new"
  originalValue="john_old"
  highlightChanged
></dw-input>

For custom equality logic:

document.querySelector('dw-input').valueEqualityChecker = (val1, val2) => {
  return String(val1).trim() === String(val2).trim();
};

Tooltip-Based Hint, Error, and Warning

<dw-input
  label="Password"
  hintInTooltip
  hint="Must be at least 8 characters"
  errorInTooltip
  error="Password is too weak"
  .errorTooltipActions=${[{ name: 'reset', label: 'Reset Password', danger: false }]}
></dw-input>

Listen for action events:

document.querySelector('dw-input').addEventListener('action', (e) => {
  console.log('Tooltip action clicked:', e.detail); // e.g. 'reset'
});

Password Field

<dw-input type="password" label="Password"></dw-input>

The visibility toggle icon is shown automatically. Listen to show/hide events:

const input = document.querySelector('dw-input');
input.addEventListener('show-password', () => console.log('Password revealed'));
input.addEventListener('hide-password', () => console.log('Password hidden'));

// Or control programmatically:
input.showPassword();
input.hidePassword();

Auto-Grow Textarea Examples

<!-- Grows from 80px to 200px, then scrolls -->
<dw-textarea .minHeight=${80} .maxHeight=${200}></dw-textarea>

<!-- Fixed height with scroll -->
<dw-textarea .minHeight=${70} .maxHeight=${70}></dw-textarea>

<!-- Prevent newline on Enter -->
<dw-textarea .minHeight=${70} .maxHeight=${70} disabledEnter></dw-textarea>

<!-- Read-only -->
<dw-textarea .minHeight=${80} .maxHeight=${200} .readOnly=${true}></dw-textarea>

2. Developer Guide / Architecture

Architecture Overview

Design Patterns

| Pattern | Where Applied | Purpose | |---------|--------------|---------| | Mixin / Composition | DwFormElement(LitElement) base class | Injects form-integration behavior (validity reporting, form participation) without inheritance conflicts | | Template Method | parseValue() and formatText() hooks | Defines the algorithm skeleton in DwInput; subclasses override specific steps to customize value serialization | | Adapter / Facade | MDCTextField instance management (_textFieldInstance) | Wraps the Material Components Web imperative API behind a reactive LitElement property model | | Strategy | valueEqualityChecker prop | Allows the equality-check algorithm to be swapped at runtime without subclassing | | Thin Specialization | DwEmailInput extends DwInput | Reuses the full DwInput implementation; only constructor defaults differ |

Module Responsibilities

| File | Responsibility | |------|----------------| | dw-input.js | Core input component — rendering, validation, MDC lifecycle, tooltip integration, value formatting hooks, icon/password handling | | mdc-text-field-css.js | Exports TextfieldStyle — the full Material Design text field CSS as a Lit css tagged template literal; imported and composed into DwInput.styles | | dw-textarea.js | Standalone auto-grow undecorated textarea; minimal styling, no MDC dependency, exposes its own props/events/methods API | | dw-email-input.js | Extends DwInput; sets type='email' and errorMessages.typeMismatch in the constructor |

Runtime Dependencies

| Package | Role | |---------|------| | lit (via LitElement) | Declarative reactive rendering and DOM update scheduling | | @material/textfield | MDCTextField imperative instance — manages floating label, ripple, and outline animations | | @dreamworld/dw-form | DwFormElement mixin — hooks the component into native <form> participation and validation lifecycles | | @dreamworld/dw-tooltip | Renders hint / error / warning tooltip overlays | | @dreamworld/dw-icon | Renders leading and trailing icons | | @dreamworld/dw-icon-button | Renders clickable trailing icon buttons (when clickableIcon=true or for password visibility) | | @dreamworld/dw-button | Renders tooltip action buttons | | @dreamworld/device-info | Detects virtual keyboard presence to conditionally adjust layout behavior | | lodash-es | Utility functions (debounce, equality checks) |