BwControl | bw-control
Overview
Use BwControl to build new form controls. The component does not do much by itself, as you have to tell it how to integrate into the form.
Usage
Example
- HTML
- Typescript
- CSS
<bw-form id="control-form">
<div class="flex-column gap-sm">
<bw-control name="accountNumber">
<bw-label>Account Number</bw-label>
<div class="flex-row gap-xs align-center" style="max-width: 300px;">
<bw-input placeholder="00" id="num-1" maxlength="2"></bw-input>
<span>-</span>
<bw-input placeholder="000" id="num-2" maxlength="3"></bw-input>
<span>-</span>
<bw-input placeholder="00" id="num-3" maxlength="2"></bw-input>
</div>
</bw-control>
</div>
<div class="margin-top-sm flex-row gap">
<bw-button type="submit">Submit</bw-button>
<bw-button type="reset">Reset</bw-button>
</div>
</bw-form>
import { combineLatest, fromEvent, map, merge, startWith } from 'rxjs';
import { createToast, BwInputCustomEvent } from 'bluewater';
const control = document.querySelector<HTMLBwControlElement>('bw-control')!
const input1 = document.querySelector<HTMLBwInputElement>('#num-1')!
const input2 = document.querySelector<HTMLBwInputElement>('#num-2')!
const input3 = document.querySelector<HTMLBwInputElement>('#num-3')!
control.focusElements = [input1, input2, input3]
control.validators = [
() => !input1.value || input1.value.length !== 2 ? ['Input 1 must be 2 characters long'] : [],
() => !input2.value || input2.value.length !== 3 ? ['Input 2 must be 3 characters long'] : [],
() => !input3.value || input3.value.length !== 2 ? ['Input 3 must be 2 characters long'] : [],
]
control.addEventListener('validityChange', ({ detail, target }) => {
if (detail?.includes('Input 1') && target.touched)
input1.focus()
else if (detail?.includes('Input 2') && target.touched)
input2.focus()
else if (detail?.includes('Input 3') && target.touched)
input3.focus()
const note = target.querySelector('bw-note')
if (detail && target.touched) {
if (note) note.textContent = detail
else control.insertAdjacentHTML('beforeend', `<bw-note invalid>${detail}</bw-note>`)
} else if (note) {
control.querySelector('bw-note')?.remove()
}
})
combineLatest({
input1: fromEvent<BwInputCustomEvent<string>>(input1, 'valueChange').pipe(
map(ev => ev.detail),
startWith('')
),
input2: fromEvent<BwInputCustomEvent<string>>(input2, 'valueChange').pipe(
map(ev => ev.detail),
startWith('')
),
input3: fromEvent<BwInputCustomEvent<string>>(input3, 'valueChange').pipe(
map(ev => ev.detail),
startWith('')
)
}).subscribe(({ input1, input2, input3 }) => {
control.value = `${input1}-${input2}-${input3}`
})
merge(
fromEvent(input1, 'focus'),
fromEvent(input2, 'focus'),
fromEvent(input3, 'focus')
).subscribe(() => {
control.touched = true
})
const form = document.querySelector<HTMLBwFormElement>('#control-form')!
form.addEventListener('formData', ev => {
createToast({
message: 'Form submitted with value: ' + JSON.stringify(ev.detail),
duration: 3000,
variant: 'bar'
}).open = true
})
bw-control:state(--user-invalid) {
bw-input {
--border: solid 1px light-dark(var(--bw-red-600), var(--bw-red-400))
}
}
Properties
| Property | Attribute | Description | Type | Default |
|---|---|---|---|---|
focusElements | focus-elements | The elements that should be focused when the control is focused. | HTMLElement[] | undefined |
originalValue | original-value | The value the control will reset to. Defaults to the initial value if not set. | any | undefined |
touched | touched | Whether or not the control is in a touched state. This is used to control it's CSS states. | boolean | false |
validators | validators | Custom validation functions the control will use to determine if it is invalid or not. | CustomValidationFn[] | undefined |
value | value | The form value of the control. | any | undefined |
Events
| Event | Description | Type |
|---|---|---|
validityChange | Emitted when the validity of the control changes. It will emit regardless if it is touched or not. | CustomEvent<string> |
Methods
checkValidity() => Promise<boolean>
Whether or not the control is currently valid.
Returns
Type: Promise<boolean>
focus() => Promise<void>
Focuses the first focusable element in the control.
Returns
Type: Promise<void>
getCustomError() => Promise<string>
Returns the current custom error message of the control.
Returns
Type: Promise<string>
getValidatorErrors() => Promise<string[]>
Returns all the current validation errors of the control.
Returns
Type: Promise<string[]>
isResetting() => Promise<boolean>
Returns whether or not the control is currently resetting.
Returns
Type: Promise<boolean>
setCustomValidity(message: string | null) => Promise<void>
Sets a custom validity message on the control. Custom errors will go away if the form is reset.
Parameters
| Name | Type | Description |
|---|---|---|
message | string |
Returns
Type: Promise<void>
© 2025 United Systems & Software - All Rights Reserved.