@oslokommune/punkt-elements
Version:
Komponentbiblioteket til Punkt, et designsystem laget av Oslo Origo
172 lines (162 loc) • 5.75 kB
text/typescript
import { html, nothing } from 'lit'
import { customElement, property } from 'lit/decorators.js'
import { classMap } from 'lit/directives/class-map.js'
import { ifDefined } from 'lit/directives/if-defined.js'
import { Ref, createRef, ref } from 'lit/directives/ref.js'
import { PktDatepickerBase } from './datepicker-base'
import { keyboardUtils, formUtils, cssUtils } from './datepicker-utils'
import { IDatepickerStrings, defaultRangeStrings } from './datepicker-types'
import { isIOS } from 'shared-utils/device-utils'
import '@/components/icon'
export class PktDatepickerRange extends PktDatepickerBase {
value: string[] = []
label: string = ''
showRangeLabels: boolean = false
strings: IDatepickerStrings = defaultRangeStrings
inputRefTo: Ref<HTMLInputElement> = createRef()
get inputElementTo(): HTMLInputElement | undefined {
return this.inputRefTo.value
}
render() {
const rangeLabelClasses = cssUtils.getRangeLabelClasses(this.showRangeLabels)
return html`
<div class="pkt-input__container">
${this.showRangeLabels
? html` <div class="pkt-input-prefix">${this.strings.generic?.from}</div> `
: nothing}
<input
class=${classMap(this.inputClasses)}
.type=${this.inputType}
id="${this.id}-input"
aria-label="${this.label} ${this.strings.generic?.from ?? 'Fra'}"
.value=${this.value[0] ?? ''}
min=${ifDefined(this.min)}
max=${ifDefined(this.max)}
placeholder=${ifDefined(this.placeholder)}
?readonly=${this.isInputReadonly}
?disabled=${this.disabled}
=${(e: MouseEvent) => {
e.preventDefault()
this.dispatchToggleCalendar(e)
}}
=${(e: TouchEvent) => {
e.preventDefault()
this.dispatchToggleCalendar(e)
}}
=${(e: KeyboardEvent) =>
keyboardUtils.handleInputKeydown(
e,
(event) => this.dispatchToggleCalendar(event),
() =>
formUtils.submitFormOrFallback(this.internals, () =>
this.inputRefTo.value?.focus(),
),
() => this.inputRefTo.value?.focus(),
() => this.inputRef.value?.blur(),
)}
=${(e: Event) => {
this.dispatchInput(e)
e.stopImmediatePropagation()
}}
=${() => {
this.dispatchFocus()
if (isIOS()) {
this.dispatchToggleCalendar(new Event('focus'))
}
}}
=${(e: FocusEvent) => {
this.dispatchBlur(e)
this.dispatchEvent(
new CustomEvent('range-blur', {
detail: {
event: e,
values: this.value,
inputType: 'from',
},
bubbles: true,
composed: true,
}),
)
}}
=${(e: Event) => {
this.dispatchChange(e)
e.stopImmediatePropagation()
}}
${ref(this.inputRef)}
/>
<div class="${classMap(rangeLabelClasses)}" id="${this.id}-to-label">
${this.strings.generic?.to}
</div>
${!this.showRangeLabels ? html` <div class="pkt-input-separator">–</div> ` : nothing}
<input
class=${classMap(this.inputClasses)}
.type=${this.inputType}
id="${this.id}-to"
aria-label="${this.label} ${this.strings.generic?.to ?? 'Til'}"
.value=${this.value[1] ?? ''}
min=${ifDefined(this.min)}
max=${ifDefined(this.max)}
placeholder=${ifDefined(this.placeholder)}
?readonly=${this.isInputReadonly}
?disabled=${this.disabled}
=${(e: MouseEvent) => {
e.preventDefault()
this.dispatchToggleCalendar(e)
}}
=${(e: TouchEvent) => {
e.preventDefault()
this.dispatchToggleCalendar(e)
}}
=${(e: KeyboardEvent) =>
keyboardUtils.handleInputKeydown(
e,
(event) => this.dispatchToggleCalendar(event),
() =>
formUtils.submitFormOrFallback(this.internals, () => this.inputRefTo.value?.blur()),
undefined,
() => this.inputRefTo.value?.blur(),
)}
=${(e: Event) => {
this.dispatchInput(e)
e.stopImmediatePropagation()
}}
=${() => {
this.dispatchFocus()
if (isIOS()) {
this.dispatchToggleCalendar(new Event('focus'))
}
}}
=${(e: FocusEvent) => {
this.dispatchBlur(e)
this.dispatchEvent(
new CustomEvent('range-blur', {
detail: {
event: e,
values: this.value,
inputType: 'to',
},
bubbles: true,
composed: true,
}),
)
}}
=${(e: Event) => {
this.dispatchChange(e)
e.stopImmediatePropagation()
}}
${ref(this.inputRefTo)}
/>
${this.renderCalendarButton()}
</div>
`
}
}
try {
customElement('pkt-datepicker-range')(PktDatepickerRange)
} catch (e) {
console.warn('Forsøker å definere <pkt-datepicker-range>, men den er allerede definert')
}