@tempots/dom
Version:
Fully-typed frontend framework alternative to React and Angular
300 lines (299 loc) • 9.21 kB
TypeScript
import { Renderable } from '../types/domain';
import { HTMLEvents } from '../types/html-events';
import { DOMContext, HandlerOptions } from '../dom/dom-context';
/**
* Attaches an event handler to the 'click' event that triggers when a checkbox is checked or unchecked.
* @param fn - The callback function to be executed when the checkbox is clicked.
* @alpha
*/
export declare const OnChecked: (fn: (event: boolean, ctx: DOMContext) => void) => Renderable;
type EventHandlerMap = {
[EN in keyof HTMLEvents]: (handler: (event: HTMLEvents[EN], ctx: DOMContext) => void, options?: HandlerOptions) => Renderable;
};
/**
* Provides type-safe event handlers for all HTML events.
*
* The `on` object is a proxy that provides access to all standard HTML events with proper
* TypeScript typing. Each event handler receives the native event object and the DOM context.
*
* Use `on.document` to attach listeners to `document` and `on.window` to attach listeners
* to `window`. These listeners are automatically removed when the component is disposed.
*
* @example
* ```typescript
* // Basic click handler
* html.button(
* on.click((event, ctx) => {
* console.log('Button clicked!', event.target)
* }),
* 'Click me'
* )
* ```
*
* @example
* ```typescript
* // Input event with value extraction
* const text = prop('')
*
* html.input(
* attr.value(text),
* on.input((event) => {
* text.value = (event.target as HTMLInputElement).value
* })
* )
* ```
*
* @example
* ```typescript
* // Multiple event handlers on same element
* html.div(
* on.mouseenter(() => console.log('Mouse entered')),
* on.mouseleave(() => console.log('Mouse left')),
* on.click(() => console.log('Clicked')),
* 'Hover and click me'
* )
* ```
*
* @example
* ```typescript
* // Keyboard event handling
* html.input(
* on.keydown((event) => {
* if (event.key === 'Enter') {
* console.log('Enter pressed!')
* event.preventDefault()
* }
* })
* )
* ```
*
* @example
* ```typescript
* // Global keyboard shortcut scoped to a component's lifetime
* html.div(
* on.document.keydown((event) => {
* if (event.key === 'Escape') {
* console.log('Escape pressed anywhere!')
* }
* }),
* 'Press Escape anywhere'
* )
* ```
*
* @example
* ```typescript
* // Window resize listener scoped to a component's lifetime
* html.div(
* on.window.resize(() => {
* console.log('Window resized!')
* }),
* 'Resize the window'
* )
* ```
*
* @public
*/
export declare const on: EventHandlerMap & {
/**
* Attaches event listeners to `document`. The listener is automatically
* removed when the component is disposed.
*/
document: EventHandlerMap;
/**
* Attaches event listeners to `window`. The listener is automatically
* removed when the component is disposed.
*/
window: EventHandlerMap;
};
/**
* Options for event handlers.
*
* @public
*/
export type EmitOptions = {
preventDefault?: boolean;
stopPropagation?: boolean;
stopImmediatePropagation?: boolean;
};
/**
* Creates an event handler that calls the provided function with the event as an argument.
* @param fn - The function to call when the event is triggered.
* @returns An event handler function that can be used with event listeners.
* @public
*/
export declare const emit: (fn: (event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Creates an event handler that extracts and emits the target element from an event.
*
* @example
* ```typescript
* html.input(
* on.input(emitTarget((input) => {
* console.log('Input value:', input.value)
* }))
* )
* ```
*
* @param fn - Callback function that receives the target element
* @returns Event handler function that can be used with event listeners
* @public
*/
export declare const emitTarget: <EL extends HTMLElement>(fn: (element: EL, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Creates an event handler that extracts and emits the string value from an input element.
*
* This utility simplifies handling input events by automatically extracting the value
* from the target element and passing it to your callback function.
*
* @example
* ```typescript
* const name = prop('')
*
* html.input(
* attr.value(name),
* on.input(emitValue(value => name.value = value))
* )
* ```
*
* @example
* ```typescript
* // With textarea
* const description = prop('')
*
* html.textarea(
* attr.value(description),
* on.input(emitValue(value => {
* description.value = value
* console.log('Description updated:', value)
* }))
* )
* ```
*
* @param fn - Callback function that receives the input element's string value
* @returns Event handler function that can be used with event listeners
* @public
*/
export declare const emitValue: (fn: (text: string, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Creates an event handler that extracts and emits the numeric value from an input element.
*
* This utility automatically converts the input's value to a number using the browser's
* built-in `valueAsNumber` property, which handles number inputs correctly and returns
* `NaN` for invalid numeric values.
*
* @example
* ```typescript
* const age = prop(0)
*
* html.input(
* attr.type('number'),
* attr.value(age.map(String)),
* on.input(emitValueAsNumber(value => {
* if (!isNaN(value)) {
* age.value = value
* }
* }))
* )
* ```
*
* @example
* ```typescript
* // With range input
* const volume = prop(50)
*
* html.input(
* attr.type('range'),
* attr.min('0'),
* attr.max('100'),
* attr.value(volume.map(String)),
* on.input(emitValueAsNumber(value => volume.value = value))
* )
* ```
*
* @param fn - Callback function that receives the input element's numeric value (may be NaN)
* @returns Event handler function that can be used with event listeners
* @public
*/
export declare const emitValueAsNumber: (fn: (num: number, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Converts the value of an HTML input element to a Date object and emits it using the provided callback function.
* @param fn - The callback function to be called with the converted Date object.
* @returns A function that can be used as an event handler for input events.
* @public
*/
export declare const emitValueAsDate: (fn: (date: Date, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Converts the value of an HTML input element to a Date object or null and emits it using the provided callback function.
* @param fn - The callback function to be called with the converted Date object or null.
* @returns A function that can be used as an event handler for input events.
* @public
*/
export declare const emitValueAsNullableDate: (fn: (date: Date | null, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Emits the value of an HTMLInputElement as a Date object.
* @param fn - The callback function to be called with the emitted Date object.
* @returns The event handler function.
* @public
*/
export declare const emitValueAsDateTime: (fn: (date: Date, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Emits the value of an HTMLInputElement as a Date object or null.
* @param fn - The callback function to be called with the emitted Date object or null.
* @returns The event handler function.
* @public
*/
export declare const emitValueAsNullableDateTime: (fn: (date: Date | null, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
/**
* Creates an event handler that extracts and emits the checked state from a checkbox or radio input.
*
* This utility simplifies handling checkbox and radio button state changes by automatically
* extracting the `checked` property from the target element.
*
* @example
* ```typescript
* const isEnabled = prop(false)
*
* html.input(
* attr.type('checkbox'),
* attr.checked(isEnabled),
* on.change(emitChecked(checked => isEnabled.value = checked))
* )
* ```
*
* @example
* ```typescript
* // With radio buttons
* const selectedOption = prop('')
*
* html.div(
* html.label(
* html.input(
* attr.type('radio'),
* attr.name('option'),
* attr.value('A'),
* on.change(emitChecked(checked => {
* if (checked) selectedOption.value = 'A'
* }))
* ),
* 'Option A'
* ),
* html.label(
* html.input(
* attr.type('radio'),
* attr.name('option'),
* attr.value('B'),
* on.change(emitChecked(checked => {
* if (checked) selectedOption.value = 'B'
* }))
* ),
* 'Option B'
* )
* )
* ```
*
* @param fn - Callback function that receives the input element's checked state
* @returns Event handler function that can be used with event listeners
* @public
*/
export declare const emitChecked: (fn: (checked: boolean, event: Event) => void, options?: EmitOptions) => (event: Event) => void;
export {};