or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

examples

edge-cases.mdreal-world-scenarios.md
index.md
tile.json

types.mddocs/reference/

TypeScript Type Reference

Complete TypeScript type definitions reference for Svelte 5, covering HTML/SVG element types, event handlers, ARIA attributes, and component utilities.

Module: svelte/elements

Table of Contents

  • Component Type Utilities
  • HTML Element Types
  • SVG Element Types
  • Event Handler Types
  • ARIA Types
  • Base DOM Types
  • Usage Examples

Component Type Utilities

These utilities help you work with component types in a type-safe manner.

Component<Props, Exports, Bindings>

interface Component<
  Props extends Record<string, any> = {},
  Exports extends Record<string, any> = {},
  Bindings extends keyof Props | '' = string
>

Represents a Svelte 5 component function with typed props, exports, and bindable properties.

Type Parameters:

  • Props - Component properties interface
  • Exports - Values exposed via export declarations
  • Bindings - Keys from Props that can be bound with bind:

Example:

import type { Component } from 'svelte';

// Declare a component type
export const MyButton: Component<
  { label: string; disabled?: boolean },
  { focus(): void },
  'disabled'
>;

ComponentProps<Comp>

type ComponentProps<Comp extends SvelteComponent | Component<any, any>>

Extracts the props type from a component. Essential for creating wrapper components or generic utilities.

Example:

import type { ComponentProps } from 'svelte';
import MyComponent from './MyComponent.svelte';

// Get props type from component
type Props = ComponentProps<typeof MyComponent>;

// Use in generic function
function withProps<TComponent extends Component<any>>(
  component: TComponent,
  props: ComponentProps<TComponent>
) {
  // ...
}

Snippet<Parameters>

interface Snippet<Parameters extends unknown[] = []>

Type for #snippet blocks that can be passed to components as props. Parameters define the expected arguments as a tuple.

Example:

import type { Snippet } from 'svelte';

interface Props {
  // Snippet with no parameters
  header?: Snippet;

  // Snippet expecting a single object parameter
  item: Snippet<[{ id: number; name: string }]>;

  // Snippet with multiple parameters
  row: Snippet<[number, string, boolean]>;
}

let { header, item, row }: Props = $props();

Usage in template:

{#if header}
  {@render header()}
{/if}

{#each items as data}
  {@render item(data)}
{/each}

HTML Element Types

The svelte/elements module exports comprehensive TypeScript types for all HTML elements. Each element type extends the base HTMLAttributes<T> interface with element-specific properties.

Common HTML Element Types

HTMLButtonAttributes

interface HTMLButtonAttributes extends HTMLAttributes<HTMLButtonElement>

Attributes for <button> elements with form integration and accessibility.

Specific Properties:

  • disabled?: boolean - Disables the button
  • form?: string - Associates with form by ID
  • formaction?: string - Override form action URL
  • formenctype?: string - Override form encoding type
  • formmethod?: string - Override form method (GET/POST)
  • formnovalidate?: boolean - Skip form validation
  • formtarget?: string - Override form target
  • name?: string - Button name for form submission
  • type?: 'submit' | 'reset' | 'button' - Button behavior type
  • value?: string - Value sent on form submission

Example:

<script lang="ts">
  import type { HTMLButtonAttributes } from 'svelte/elements';

  let buttonProps: HTMLButtonAttributes = {
    type: 'submit',
    disabled: false,
    onclick: (e) => console.log('clicked', e.currentTarget)
  };
</script>

<button {...buttonProps}>Submit</button>

HTMLInputAttributes

interface HTMLInputAttributes extends HTMLAttributes<HTMLInputElement>

Comprehensive attributes for <input> elements covering all input types.

Specific Properties:

  • accept?: string - File type filter (file inputs)
  • alt?: string - Alternative text (image inputs)
  • autocomplete?: string - Browser autocomplete hint
  • capture?: boolean | string - Camera capture mode (file inputs)
  • checked?: boolean - Checked state (checkbox/radio)
  • disabled?: boolean - Disables the input
  • form?: string - Associates with form by ID
  • list?: string - ID of datalist for suggestions
  • max?: number | string - Maximum value
  • maxlength?: number - Maximum character length
  • min?: number | string - Minimum value
  • minlength?: number - Minimum character length
  • multiple?: boolean - Allow multiple selections
  • name?: string - Input name for form submission
  • pattern?: string - Validation regex pattern
  • placeholder?: string - Placeholder text
  • readonly?: boolean - Prevents editing
  • required?: boolean - Marks as required field
  • size?: number - Visual width in characters
  • step?: number | string - Value increment step
  • type?: string - Input type (text, email, number, etc.)
  • value?: string | number - Input value

Example:

<script lang="ts">
  import type { HTMLInputAttributes } from 'svelte/elements';

  let emailInput: HTMLInputAttributes = {
    type: 'email',
    required: true,
    placeholder: 'user@example.com',
    autocomplete: 'email',
    oninput: (e) => {
      const target = e.currentTarget as HTMLInputElement;
      console.log(target.value);
    }
  };
</script>

<input {...emailInput} bind:value={email} />

HTMLFormAttributes

interface HTMLFormAttributes extends HTMLAttributes<HTMLFormElement>

Attributes for <form> elements controlling submission behavior.

Specific Properties:

  • acceptCharset?: string - Character encoding for submission
  • action?: string - Form submission URL
  • autocomplete?: string - Form-wide autocomplete behavior
  • enctype?: string - Encoding type for POST requests
  • method?: string - HTTP method (GET/POST)
  • name?: string - Form name
  • novalidate?: boolean - Skip validation on submit
  • target?: string - Where to display response

Example:

<script lang="ts">
  import type { HTMLFormAttributes } from 'svelte/elements';

  let formProps: HTMLFormAttributes = {
    method: 'POST',
    action: '/api/submit',
    novalidate: false,
    onsubmit: async (e) => {
      e.preventDefault();
      const form = e.currentTarget as HTMLFormElement;
      const data = new FormData(form);
      // Handle submission
    }
  };
</script>

<form {...formProps}>
  <!-- form fields -->
</form>

HTMLAnchorAttributes

interface HTMLAnchorAttributes extends HTMLAttributes<HTMLAnchorElement>

Attributes for <a> link elements.

Specific Properties:

  • download?: string - Prompts download with filename
  • href?: string - Link destination URL
  • hreflang?: string - Language of linked resource
  • media?: string - Media query for link relevance
  • ping?: string - Space-separated URLs to ping
  • referrerpolicy?: ReferrerPolicy - Referrer header policy
  • rel?: string - Relationship to linked resource
  • target?: string - Where to open link (_blank, _self, etc.)
  • type?: string - MIME type of linked resource

Example:

<script lang="ts">
  import type { HTMLAnchorAttributes } from 'svelte/elements';

  let linkProps: HTMLAnchorAttributes = {
    href: '/dashboard',
    target: '_blank',
    rel: 'noopener noreferrer',
    onclick: (e) => {
      console.log('navigating to', e.currentTarget.href);
    }
  };
</script>

<a {...linkProps}>Go to Dashboard</a>

HTMLImageAttributes

interface HTMLImgAttributes extends HTMLAttributes<HTMLImageElement>

Attributes for <img> elements with modern image features.

Specific Properties:

  • alt?: string - Alternative text (required for accessibility)
  • crossorigin?: 'anonymous' | 'use-credentials' - CORS mode
  • decoding?: 'async' | 'auto' | 'sync' - Decode hint
  • height?: number | string - Display height
  • loading?: 'eager' | 'lazy' - Loading strategy
  • referrerpolicy?: ReferrerPolicy - Referrer header policy
  • sizes?: string - Size hints for responsive images
  • src?: string - Image source URL
  • srcset?: string - Responsive image sources
  • width?: number | string - Display width

Example:

<script lang="ts">
  import type { HTMLImgAttributes } from 'svelte/elements';

  let imgProps: HTMLImgAttributes = {
    src: '/images/hero.jpg',
    alt: 'Hero image description',
    loading: 'lazy',
    width: 800,
    height: 600,
    onload: () => console.log('Image loaded'),
    onerror: () => console.error('Failed to load image')
  };
</script>

<img {...imgProps} />

Container and Layout Elements

HTMLDivAttributes

interface HTMLDivAttributes extends HTMLAttributes<HTMLDivElement>

Generic container element attributes. Since <div> has no specific attributes, this is essentially HTMLAttributes<HTMLDivElement>.

HTMLSpanAttributes

interface HTMLSpanAttributes extends HTMLAttributes<HTMLSpanElement>

Inline container element attributes. Like div, extends only base attributes.

HTMLTableAttributes

interface HTMLTableAttributes extends HTMLAttributes<HTMLTableElement>

Attributes for <table> elements.

Specific Properties:

  • align?: string - (Deprecated) Table alignment
  • bgcolor?: string - (Deprecated) Background color
  • border?: number | string - (Deprecated) Border width
  • cellpadding?: number | string - (Deprecated) Cell padding
  • cellspacing?: number | string - (Deprecated) Cell spacing
  • frame?: string - (Deprecated) Frame visibility
  • rules?: string - (Deprecated) Rules visibility
  • summary?: string - (Deprecated) Table summary
  • width?: number | string - (Deprecated) Table width

Note: Most specific table attributes are deprecated. Use CSS for styling instead.

Form and Input Elements

Additional form-related element types:

  • HTMLTextareaAttributes - Multi-line text input
  • HTMLSelectAttributes - Dropdown selection
  • HTMLOptionAttributes - Option within select
  • HTMLLabelAttributes - Label for form controls
  • HTMLFieldsetAttributes - Grouping form controls
  • HTMLLegendAttributes - Caption for fieldset
  • HTMLOutputAttributes - Result of calculation
  • HTMLProgressAttributes - Progress indicator
  • HTMLMeterAttributes - Scalar measurement

Media Elements

  • HTMLVideoAttributes - Video playback
  • HTMLAudioAttributes - Audio playback
  • HTMLSourceAttributes - Media source
  • HTMLTrackAttributes - Text tracks for media

Document Metadata

  • HTMLMetaAttributes - Document metadata
  • HTMLLinkAttributes - External resource links
  • HTMLStyleAttributes - Embedded styles
  • HTMLScriptAttributes - Embedded or external scripts
  • HTMLBaseAttributes - Base URL for relative links
  • HTMLTitleAttributes - Document title

Semantic Elements

  • HTMLArticleAttributes - Self-contained content
  • HTMLSectionAttributes - Document section
  • HTMLNavAttributes - Navigation links
  • HTMLAsideAttributes - Tangential content
  • HTMLHeaderAttributes - Introductory content
  • HTMLFooterAttributes - Footer content
  • HTMLMainAttributes - Main content
  • HTMLFigureAttributes - Self-contained figure
  • HTMLFigcaptionAttributes - Figure caption

Complete List of HTML Element Types

All HTML element attribute types follow the pattern HTML[Element]Attributes:

HTMLAnchorAttributes        // <a>
HTMLAreaAttributes          // <area>
HTMLAudioAttributes         // <audio>
HTMLBaseAttributes          // <base>
HTMLBlockquoteAttributes    // <blockquote>
HTMLButtonAttributes        // <button>
HTMLCanvasAttributes        // <canvas>
HTMLColAttributes           // <col>
HTMLColgroupAttributes      // <colgroup>
HTMLDataAttributes          // <data>
HTMLDetailsAttributes       // <details>
HTMLDialogAttributes        // <dialog>
HTMLDivAttributes           // <div>
HTMLEmbedAttributes         // <embed>
HTMLFieldsetAttributes      // <fieldset>
HTMLFormAttributes          // <form>
HTMLHtmlAttributes          // <html>
HTMLIframeAttributes        // <iframe>
HTMLImgAttributes           // <img>
HTMLInputAttributes         // <input>
HTMLInsAttributes           // <ins>
HTMLDelAttributes           // <del>
HTMLKeygenAttributes        // <keygen>
HTMLLabelAttributes         // <label>
HTMLLiAttributes            // <li>
HTMLLinkAttributes          // <link>
HTMLMapAttributes           // <map>
HTMLMenuAttributes          // <menu>
HTMLMetaAttributes          // <meta>
HTMLMeterAttributes         // <meter>
HTMLObjectAttributes        // <object>
HTMLOlAttributes            // <ol>
HTMLOptgroupAttributes      // <optgroup>
HTMLOptionAttributes        // <option>
HTMLOutputAttributes        // <output>
HTMLParamAttributes         // <param>
HTMLProgressAttributes      // <progress>
HTMLQuoteAttributes         // <q>
HTMLScriptAttributes        // <script>
HTMLSelectAttributes        // <select>
HTMLSlotAttributes          // <slot>
HTMLSourceAttributes        // <source>
HTMLSpanAttributes          // <span>
HTMLStyleAttributes         // <style>
HTMLTableAttributes         // <table>
HTMLTdAttributes            // <td>
HTMLTemplateAttributes      // <template>
HTMLTextareaAttributes      // <textarea>
HTMLThAttributes            // <th>
HTMLTimeAttributes          // <time>
HTMLTrackAttributes         // <track>
HTMLVideoAttributes         // <video>
HTMLWebViewAttributes       // <webview>

SVG Element Types

SVG element types provide comprehensive typing for Scalable Vector Graphics elements in Svelte.

SVGAttributes<T>

interface SVGAttributes<T extends EventTarget> extends AriaAttributes, DOMAttributes<T>

Base interface for all SVG elements. Includes common SVG attributes and presentation properties.

Common SVG Properties:

  • clip-path?: string - Clipping path reference
  • color?: string - Color for current element
  • fill?: string - Fill color/pattern
  • fill-opacity?: number | string - Fill opacity
  • fill-rule?: 'nonzero' | 'evenodd' | 'inherit' - Fill algorithm
  • stroke?: string - Stroke color/pattern
  • stroke-dasharray?: string | number - Dash pattern
  • stroke-dashoffset?: number | string - Dash offset
  • stroke-linecap?: 'butt' | 'round' | 'square' | 'inherit' - Line cap style
  • stroke-linejoin?: 'miter' | 'round' | 'bevel' | 'inherit' - Line join style
  • stroke-opacity?: number | string - Stroke opacity
  • stroke-width?: number | string - Stroke width
  • transform?: string - Transform operations
  • opacity?: number | string - Overall opacity

Common SVG Element Types

SVGCircleAttributes

type SVGCircleAttributes = SVGAttributes<SVGCircleElement>

Attributes for <circle> elements.

Example:

<script lang="ts">
  import type { SVGCircleAttributes } from 'svelte/elements';

  let circleProps: SVGCircleAttributes = {
    cx: 50,
    cy: 50,
    r: 40,
    fill: 'blue',
    stroke: 'black',
    'stroke-width': 2,
    onclick: (e) => console.log('Circle clicked')
  };
</script>

<svg viewBox="0 0 100 100">
  <circle {...circleProps} />
</svg>

SVGPathAttributes

type SVGPathAttributes = SVGAttributes<SVGPathElement>

Attributes for <path> elements, the most versatile SVG drawing element.

Example:

<script lang="ts">
  import type { SVGPathAttributes } from 'svelte/elements';

  let pathProps: SVGPathAttributes = {
    d: 'M 10 80 C 40 10, 65 10, 95 80 S 150 150, 180 80',
    fill: 'transparent',
    stroke: 'purple',
    'stroke-width': 3,
    onmouseover: (e) => {
      e.currentTarget.setAttribute('stroke', 'red');
    }
  };
</script>

<svg viewBox="0 0 200 200">
  <path {...pathProps} />
</svg>

SVGRectAttributes

type SVGRectAttributes = SVGAttributes<SVGRectElement>

Attributes for <rect> rectangle elements.

Example:

<script lang="ts">
  import type { SVGRectAttributes } from 'svelte/elements';

  let rectProps: SVGRectAttributes = {
    x: 10,
    y: 10,
    width: 80,
    height: 60,
    rx: 5,  // rounded corners
    ry: 5,
    fill: 'lightblue',
    stroke: 'navy'
  };
</script>

<svg viewBox="0 0 100 100">
  <rect {...rectProps} />
</svg>

SVGLineAttributes

type SVGLineAttributes = SVGAttributes<SVGLineElement>

Attributes for <line> elements.

Example:

<script lang="ts">
  import type { SVGLineAttributes } from 'svelte/elements';

  let lineProps: SVGLineAttributes = {
    x1: 0,
    y1: 0,
    x2: 100,
    y2: 100,
    stroke: 'black',
    'stroke-width': 2
  };
</script>

<svg viewBox="0 0 100 100">
  <line {...lineProps} />
</svg>

SVGEllipseAttributes

type SVGEllipseAttributes = SVGAttributes<SVGEllipseElement>

Attributes for <ellipse> elements.

Example:

<script lang="ts">
  import type { SVGEllipseAttributes } from 'svelte/elements';

  let ellipseProps: SVGEllipseAttributes = {
    cx: 50,
    cy: 50,
    rx: 40,  // x-axis radius
    ry: 25,  // y-axis radius
    fill: 'yellow',
    stroke: 'orange'
  };
</script>

<svg viewBox="0 0 100 100">
  <ellipse {...ellipseProps} />
</svg>

SVGPolygonAttributes

type SVGPolygonAttributes = SVGAttributes<SVGPolygonElement>

Attributes for <polygon> closed shape elements.

Example:

<script lang="ts">
  import type { SVGPolygonAttributes } from 'svelte/elements';

  // Star shape
  let polygonProps: SVGPolygonAttributes = {
    points: '50,15 61,35 82,35 66,48 73,68 50,55 27,68 34,48 18,35 39,35',
    fill: 'gold',
    stroke: 'darkorange',
    'stroke-width': 2
  };
</script>

<svg viewBox="0 0 100 100">
  <polygon {...polygonProps} />
</svg>

SVG Filter and Effect Elements

  • SVGFEBlendElement - Blend two images
  • SVGFEColorMatrixElement - Color transformation matrix
  • SVGFEComponentTransferElement - Component-wise color remapping
  • SVGFECompositeElement - Combine images with Porter-Duff operations
  • SVGFEConvolveMatrixElement - Matrix convolution filter
  • SVGFEDiffuseLightingElement - Diffuse lighting effect
  • SVGFEDisplacementMapElement - Pixel displacement
  • SVGFEDropShadowElement - Drop shadow effect
  • SVGFEGaussianBlurElement - Gaussian blur
  • SVGFEMorphologyElement - Morphological operations

Complete List of SVG Element Types

All SVG elements use SVGAttributes<SVG[Element]Element>:

SVGAttributes<SVGSVGElement>              // <svg>
SVGAttributes<SVGCircleElement>           // <circle>
SVGAttributes<SVGEllipseElement>          // <ellipse>
SVGAttributes<SVGLineElement>             // <line>
SVGAttributes<SVGPathElement>             // <path>
SVGAttributes<SVGPolygonElement>          // <polygon>
SVGAttributes<SVGPolylineElement>         // <polyline>
SVGAttributes<SVGRectElement>             // <rect>
SVGAttributes<SVGGElement>                // <g>
SVGAttributes<SVGDefsElement>             // <defs>
SVGAttributes<SVGClipPathElement>         // <clipPath>
SVGAttributes<SVGLinearGradientElement>   // <linearGradient>
SVGAttributes<SVGRadialGradientElement>   // <radialGradient>
SVGAttributes<SVGStopElement>             // <stop>
SVGAttributes<SVGTextElement>             // <text>
SVGAttributes<SVGTSpanElement>            // <tspan>
SVGAttributes<SVGImageElement>            // <image>
SVGAttributes<SVGUseElement>              // <use>
SVGAttributes<SVGSymbolElement>           // <symbol>
SVGAttributes<SVGMarkerElement>           // <marker>
SVGAttributes<SVGMaskElement>             // <mask>
SVGAttributes<SVGPatternElement>          // <pattern>
SVGAttributes<SVGFilterElement>           // <filter>
// ... and all filter effect elements

Event Handler Types

Event handler types provide strongly-typed event handling with proper currentTarget typing.

EventHandler<E, T>

type EventHandler<E extends Event = Event, T extends EventTarget = Element> = (
  event: E & { currentTarget: EventTarget & T }
) => any

Generic event handler type. The event object's currentTarget is typed to the specific element type.

Specific Event Handler Types

Mouse Events

type MouseEventHandler<T extends EventTarget> = EventHandler<MouseEvent, T>

Handles all mouse-related events: click, dblclick, mousedown, mouseup, mousemove, mouseenter, mouseleave, mouseover, mouseout.

Example:

<script lang="ts">
  import type { MouseEventHandler } from 'svelte/elements';

  const handleClick: MouseEventHandler<HTMLButtonElement> = (e) => {
    console.log('Button clicked at', e.clientX, e.clientY);
    console.log('Button element:', e.currentTarget); // Typed as HTMLButtonElement
  };
</script>

<button onclick={handleClick}>Click me</button>

Keyboard Events

type KeyboardEventHandler<T extends EventTarget> = EventHandler<KeyboardEvent, T>

Handles keyboard events: keydown, keyup, keypress.

Example:

<script lang="ts">
  import type { KeyboardEventHandler } from 'svelte/elements';

  const handleKeydown: KeyboardEventHandler<HTMLInputElement> = (e) => {
    if (e.key === 'Enter') {
      console.log('Enter pressed:', e.currentTarget.value);
    }
  };
</script>

<input type="text" onkeydown={handleKeydown} />

Form Events

type FormEventHandler<T extends EventTarget> = EventHandler<Event, T>
type ChangeEventHandler<T extends EventTarget> = EventHandler<Event, T>

Handles form-related events: input, change, reset, invalid, formdata.

Example:

<script lang="ts">
  import type { FormEventHandler, ChangeEventHandler } from 'svelte/elements';

  const handleInput: FormEventHandler<HTMLInputElement> = (e) => {
    console.log('Input value:', e.currentTarget.value);
  };

  const handleChange: ChangeEventHandler<HTMLSelectElement> = (e) => {
    console.log('Selected:', e.currentTarget.value);
  };

  const handleSubmit: FormEventHandler<HTMLFormElement> = (e) => {
    e.preventDefault();
    const formData = new FormData(e.currentTarget);
    console.log('Form submitted:', Object.fromEntries(formData));
  };
</script>

<form onsubmit={handleSubmit}>
  <input type="text" oninput={handleInput} />
  <select onchange={handleChange}>
    <option value="a">Option A</option>
    <option value="b">Option B</option>
  </select>
  <button type="submit">Submit</button>
</form>

Focus Events

type FocusEventHandler<T extends EventTarget> = EventHandler<FocusEvent, T>

Handles focus-related events: focus, blur, focusin, focusout.

Example:

<script lang="ts">
  import type { FocusEventHandler } from 'svelte/elements';

  const handleFocus: FocusEventHandler<HTMLInputElement> = (e) => {
    e.currentTarget.style.borderColor = 'blue';
  };

  const handleBlur: FocusEventHandler<HTMLInputElement> = (e) => {
    e.currentTarget.style.borderColor = '';
  };
</script>

<input onfocus={handleFocus} onblur={handleBlur} />

Touch Events

type TouchEventHandler<T extends EventTarget> = EventHandler<TouchEvent, T>

Handles touch events: touchstart, touchmove, touchend, touchcancel.

Example:

<script lang="ts">
  import type { TouchEventHandler } from 'svelte/elements';

  let startX = 0;

  const handleTouchStart: TouchEventHandler<HTMLDivElement> = (e) => {
    startX = e.touches[0].clientX;
  };

  const handleTouchMove: TouchEventHandler<HTMLDivElement> = (e) => {
    const currentX = e.touches[0].clientX;
    const diff = currentX - startX;
    e.currentTarget.style.transform = `translateX(${diff}px)`;
  };
</script>

<div ontouchstart={handleTouchStart} ontouchmove={handleTouchMove}>
  Swipeable element
</div>

Pointer Events

type PointerEventHandler<T extends EventTarget> = EventHandler<PointerEvent, T>

Handles unified pointer events (mouse, touch, pen): pointerdown, pointerup, pointermove, pointerenter, pointerleave, pointerover, pointerout, pointercancel, gotpointercapture, lostpointercapture.

Example:

<script lang="ts">
  import type { PointerEventHandler } from 'svelte/elements';

  const handlePointerDown: PointerEventHandler<HTMLCanvasElement> = (e) => {
    const canvas = e.currentTarget;
    const rect = canvas.getBoundingClientRect();
    const x = e.clientX - rect.left;
    const y = e.clientY - rect.top;

    // Draw at pointer position
    const ctx = canvas.getContext('2d');
    if (ctx) {
      ctx.fillRect(x - 2, y - 2, 4, 4);
    }
  };
</script>

<canvas onpointerdown={handlePointerDown} />

Drag Events

type DragEventHandler<T extends EventTarget> = EventHandler<DragEvent, T>

Handles drag-and-drop events: drag, dragstart, dragend, dragenter, dragleave, dragover, drop.

Example:

<script lang="ts">
  import type { DragEventHandler } from 'svelte/elements';

  const handleDragOver: DragEventHandler<HTMLDivElement> = (e) => {
    e.preventDefault();
    e.currentTarget.style.backgroundColor = 'lightblue';
  };

  const handleDrop: DragEventHandler<HTMLDivElement> = (e) => {
    e.preventDefault();
    e.currentTarget.style.backgroundColor = '';
    const data = e.dataTransfer?.getData('text/plain');
    console.log('Dropped:', data);
  };
</script>

<div ondragover={handleDragOver} ondrop={handleDrop}>
  Drop zone
</div>

Animation and Transition Events

type AnimationEventHandler<T extends EventTarget> = EventHandler<AnimationEvent, T>
type TransitionEventHandler<T extends EventTarget> = EventHandler<TransitionEvent, T>

Handles CSS animation and transition events.

Example:

<script lang="ts">
  import type { AnimationEventHandler, TransitionEventHandler } from 'svelte/elements';

  const handleAnimationEnd: AnimationEventHandler<HTMLDivElement> = (e) => {
    console.log('Animation ended:', e.animationName);
  };

  const handleTransitionEnd: TransitionEventHandler<HTMLDivElement> = (e) => {
    console.log('Transition ended:', e.propertyName);
  };
</script>

<div onanimationend={handleAnimationEnd} ontransitionend={handleTransitionEnd}>
  Animated element
</div>

Other Event Handler Types

type ClipboardEventHandler<T>     // copy, cut, paste
type CompositionEventHandler<T>   // compositionstart, compositionupdate, compositionend
type WheelEventHandler<T>         // wheel
type UIEventHandler<T>            // scroll, resize
type GamepadEventHandler<T>       // gamepadconnected, gamepaddisconnected
type MessageEventHandler<T>       // message, messageerror
type ToggleEventHandler<T>        // toggle, beforetoggle (popover)

ARIA Types

ARIA (Accessible Rich Internet Applications) types ensure accessibility compliance.

AriaRole

type AriaRole =
  | 'alert' | 'alertdialog' | 'application' | 'article' | 'banner'
  | 'button' | 'cell' | 'checkbox' | 'columnheader' | 'combobox'
  | 'complementary' | 'contentinfo' | 'definition' | 'dialog'
  | 'directory' | 'document' | 'feed' | 'figure' | 'form'
  | 'grid' | 'gridcell' | 'group' | 'heading' | 'img'
  | 'link' | 'list' | 'listbox' | 'listitem' | 'log'
  | 'main' | 'marquee' | 'math' | 'menu' | 'menubar'
  | 'menuitem' | 'menuitemcheckbox' | 'menuitemradio' | 'navigation'
  | 'none' | 'note' | 'option' | 'presentation' | 'progressbar'
  | 'radio' | 'radiogroup' | 'region' | 'row' | 'rowgroup'
  | 'rowheader' | 'scrollbar' | 'search' | 'searchbox'
  | 'separator' | 'slider' | 'spinbutton' | 'status' | 'switch'
  | 'tab' | 'table' | 'tablist' | 'tabpanel' | 'term'
  | 'textbox' | 'timer' | 'toolbar' | 'tooltip' | 'tree'
  | 'treegrid' | 'treeitem'
  | (string & {})

Defines the semantic role of an element for assistive technologies. The union with (string & {}) allows custom roles while preserving autocomplete.

Example:

<script lang="ts">
  import type { AriaRole } from 'svelte/elements';

  let role: AriaRole = 'button';
</script>

<div role={role} tabindex="0">
  Custom button
</div>

AriaAttributes

interface AriaAttributes

Complete set of WAI-ARIA 1.1 attributes for accessibility.

State Attributes:

  • aria-busy?: Booleanish - Element is being modified
  • aria-checked?: boolean | 'false' | 'mixed' | 'true' - Checkbox/radio state
  • aria-disabled?: Booleanish - Element is disabled
  • aria-expanded?: Booleanish - Expandable element state
  • aria-hidden?: Booleanish - Element is hidden from accessibility tree
  • aria-invalid?: boolean | 'false' | 'true' | 'grammar' | 'spelling' - Validation state
  • aria-pressed?: boolean | 'false' | 'mixed' | 'true' - Toggle button state
  • aria-readonly?: Booleanish - Element is read-only
  • aria-required?: Booleanish - Field is required
  • aria-selected?: Booleanish - Selection state

Relationship Attributes:

  • aria-activedescendant?: string - ID of active descendant
  • aria-controls?: string - IDs of controlled elements
  • aria-describedby?: string - IDs of describing elements
  • aria-details?: string - ID of detailed description
  • aria-errormessage?: string - ID of error message
  • aria-flowto?: string - IDs for reading order
  • aria-labelledby?: string - IDs of labeling elements
  • aria-owns?: string - IDs of owned elements

Widget Attributes:

  • aria-autocomplete?: 'none' | 'inline' | 'list' | 'both' - Autocomplete behavior
  • aria-haspopup?: boolean | 'false' | 'true' | 'menu' | 'listbox' | 'tree' | 'grid' | 'dialog' - Popup type
  • aria-level?: number - Hierarchical level
  • aria-modal?: Booleanish - Element is modal
  • aria-multiline?: Booleanish - Textbox is multiline
  • aria-multiselectable?: Booleanish - Multiple selection allowed
  • aria-orientation?: 'horizontal' | 'vertical' - Element orientation
  • aria-placeholder?: string - Placeholder text
  • aria-valuemax?: number - Maximum value
  • aria-valuemin?: number - Minimum value
  • aria-valuenow?: number - Current value
  • aria-valuetext?: string - Human-readable value text

Live Region Attributes:

  • aria-atomic?: Booleanish - Announce entire region or just changes
  • aria-live?: 'off' | 'assertive' | 'polite' - Live region priority
  • aria-relevant?: string - Types of changes to announce

Drag-and-Drop Attributes:

  • aria-dropeffect?: 'none' | 'copy' | 'execute' | 'link' | 'move' | 'popup' - Drop operation
  • aria-grabbed?: Booleanish - Element is grabbed

Grid Attributes:

  • aria-colcount?: number - Total columns
  • aria-colindex?: number - Column index
  • aria-colspan?: number - Columns spanned
  • aria-rowcount?: number - Total rows
  • aria-rowindex?: number - Row index
  • aria-rowspan?: number - Rows spanned

Example:

<script lang="ts">
  import type { AriaAttributes } from 'svelte/elements';

  let expanded = $state(false);

  let triggerAttrs: AriaAttributes = {
    'aria-expanded': expanded,
    'aria-controls': 'dropdown-menu',
    'aria-haspopup': 'menu'
  };

  let menuAttrs: AriaAttributes = {
    'aria-hidden': !expanded,
    'aria-labelledby': 'menu-trigger'
  };
</script>

<button id="menu-trigger" {...triggerAttrs} onclick={() => expanded = !expanded}>
  Menu
</button>
<div id="dropdown-menu" role="menu" {...menuAttrs}>
  <div role="menuitem">Item 1</div>
  <div role="menuitem">Item 2</div>
</div>

Base DOM Types

DOMAttributes<T>

interface DOMAttributes<T extends EventTarget>

Base interface for all DOM elements, providing:

  • Event handlers for all standard DOM events (both on: and on syntax)
  • Capture phase event handlers (oncapture suffix)
  • Svelte-specific events (introstart, introend, outrostart, outroend)
  • Element bindings (bind:clientWidth, bind:clientHeight, etc.)
  • Special children property for Snippet type

Event Handler Properties:

All standard DOM events are available in three forms:

'on:click'?: MouseEventHandler<T>    // Svelte syntax
onclick?: MouseEventHandler<T>       // Standard syntax
onclickcapture?: MouseEventHandler<T> // Capture phase

Dimensional Bindings:

readonly 'bind:contentRect'?: DOMRectReadOnly
readonly 'bind:contentBoxSize'?: Array<ResizeObserverSize>
readonly 'bind:borderBoxSize'?: Array<ResizeObserverSize>
readonly 'bind:devicePixelContentBoxSize'?: Array<ResizeObserverSize>
readonly 'bind:clientWidth'?: number
readonly 'bind:clientHeight'?: number

Example:

<script lang="ts">
  import type { DOMAttributes } from 'svelte/elements';

  let width = $state(0);
  let height = $state(0);

  let divProps: DOMAttributes<HTMLDivElement> = {
    onclick: (e) => console.log('Clicked'),
    'on:mouseover': (e) => console.log('Mouse over'),
    onclickcapture: (e) => console.log('Click captured')
  };
</script>

<div
  {...divProps}
  bind:clientWidth={width}
  bind:clientHeight={height}
>
  Size: {width} x {height}
</div>

HTMLAttributes<T>

interface HTMLAttributes<T extends EventTarget> extends AriaAttributes, DOMAttributes<T>

Base for all HTML elements. Includes all standard HTML global attributes:

Core Attributes:

  • id?: string - Unique identifier
  • class?: string - CSS classes
  • style?: string - Inline styles
  • title?: string - Advisory information

Metadata:

  • accesskey?: string - Keyboard shortcut
  • contenteditable?: Booleanish | 'inherit' - Editable content
  • dir?: 'ltr' | 'rtl' | 'auto' - Text direction
  • draggable?: Booleanish - Draggable element
  • hidden?: boolean | 'hidden' | 'until-found' - Hidden element
  • lang?: string - Language code
  • spellcheck?: Booleanish - Spell checking
  • tabindex?: number - Tab order
  • translate?: 'yes' | 'no' - Translation behavior

Microdata:

  • itemid?: string - Microdata item ID
  • itemprop?: string - Microdata property
  • itemref?: string - Microdata references
  • itemscope?: boolean - Microdata scope
  • itemtype?: string - Microdata type

Custom Data:

  • [key: data-${string}]: any - Data attributes (data-*)

Svelte Directives:

  • use?: Action - Apply action directive
  • transition?: TransitionFn - Transition effect
  • in?: TransitionFn - Intro transition
  • out?: TransitionFn - Outro transition
  • animate?: AnimationFn - Animation on reordering

Usage Examples

Typing Component Props with Element Attributes

<script lang="ts">
  import type { HTMLButtonAttributes } from 'svelte/elements';

  interface Props extends HTMLButtonAttributes {
    variant?: 'primary' | 'secondary';
    loading?: boolean;
  }

  let {
    variant = 'primary',
    loading = false,
    children,
    ...buttonProps
  }: Props = $props();
</script>

<button
  {...buttonProps}
  class="btn btn-{variant}"
  disabled={buttonProps.disabled || loading}
>
  {#if loading}
    Loading...
  {:else}
    {@render children?.()}
  {/if}
</button>

Creating Typed Action Functions

<script lang="ts">
  import type { Action } from 'svelte/action';
  import type { HTMLInputAttributes } from 'svelte/elements';

  interface TooltipParams {
    text: string;
    position?: 'top' | 'bottom';
  }

  const tooltip: Action<HTMLElement, TooltipParams> = (node, params) => {
    let tooltipEl: HTMLDivElement | null = null;

    function show() {
      tooltipEl = document.createElement('div');
      tooltipEl.textContent = params.text;
      tooltipEl.className = `tooltip tooltip-${params.position ?? 'top'}`;
      document.body.appendChild(tooltipEl);
    }

    function hide() {
      tooltipEl?.remove();
      tooltipEl = null;
    }

    node.addEventListener('mouseenter', show);
    node.addEventListener('mouseleave', hide);

    return {
      update(newParams) {
        params = newParams;
      },
      destroy() {
        hide();
        node.removeEventListener('mouseenter', show);
        node.removeEventListener('mouseleave', hide);
      }
    };
  };

  let inputProps: HTMLInputAttributes = {
    type: 'text',
    placeholder: 'Enter text...'
  };
</script>

<input {...inputProps} use:tooltip={{ text: 'This is a tooltip' }} />

Generic Component with Typed Events

<script lang="ts" generics="T extends HTMLElement">
  import type { HTMLAttributes, MouseEventHandler } from 'svelte/elements';

  interface Props extends HTMLAttributes<T> {
    element?: keyof HTMLElementTagNameMap;
    onCustomClick?: MouseEventHandler<T>;
  }

  let {
    element = 'div',
    onCustomClick,
    children,
    ...attrs
  }: Props = $props();

  const handleClick: MouseEventHandler<T> = (e) => {
    console.log('Internal handling:', e.currentTarget);
    onCustomClick?.(e);
  };
</script>

<svelte:element this={element} {...attrs} onclick={handleClick}>
  {@render children?.()}
</svelte:element>

Form with Typed Event Handlers

<script lang="ts">
  import type {
    HTMLFormAttributes,
    FormEventHandler,
    ChangeEventHandler
  } from 'svelte/elements';

  let formData = $state({
    username: '',
    email: '',
    role: 'user'
  });

  const handleSubmit: FormEventHandler<HTMLFormElement> = (e) => {
    e.preventDefault();
    console.log('Submitted:', formData);
  };

  const handleUsernameInput: FormEventHandler<HTMLInputElement> = (e) => {
    formData.username = e.currentTarget.value;
  };

  const handleEmailInput: FormEventHandler<HTMLInputElement> = (e) => {
    formData.email = e.currentTarget.value;
  };

  const handleRoleChange: ChangeEventHandler<HTMLSelectElement> = (e) => {
    formData.role = e.currentTarget.value;
  };
</script>

<form onsubmit={handleSubmit}>
  <input
    type="text"
    name="username"
    value={formData.username}
    oninput={handleUsernameInput}
    required
  />

  <input
    type="email"
    name="email"
    value={formData.email}
    oninput={handleEmailInput}
    required
  />

  <select
    name="role"
    value={formData.role}
    onchange={handleRoleChange}
  >
    <option value="user">User</option>
    <option value="admin">Admin</option>
  </select>

  <button type="submit">Submit</button>
</form>

SVG Component with Typed Attributes

<script lang="ts">
  import type { SVGAttributes } from 'svelte/elements';

  interface Props {
    size?: number;
    color?: string;
    onclick?: SVGAttributes<SVGSVGElement>['onclick'];
  }

  let { size = 24, color = 'currentColor', onclick }: Props = $props();

  let svgAttrs: SVGAttributes<SVGSVGElement> = {
    width: size,
    height: size,
    viewBox: '0 0 24 24',
    fill: 'none',
    stroke: color,
    'stroke-width': 2,
    'stroke-linecap': 'round',
    'stroke-linejoin': 'round',
    onclick
  };
</script>

<svg {...svgAttrs}>
  <path d="M12 2L2 7l10 5 10-5-10-5z" />
  <path d="M2 17l10 5 10-5M2 12l10 5 10-5" />
</svg>

Accessible Component with ARIA

<script lang="ts">
  import type { HTMLAttributes, AriaAttributes, KeyboardEventHandler } from 'svelte/elements';

  interface Props extends HTMLAttributes<HTMLDivElement> {
    label: string;
    checked?: boolean;
    onToggle?: (checked: boolean) => void;
  }

  let { label, checked = $bindable(false), onToggle, ...attrs }: Props = $props();

  const toggle = () => {
    checked = !checked;
    onToggle?.(checked);
  };

  const handleKeydown: KeyboardEventHandler<HTMLDivElement> = (e) => {
    if (e.key === ' ' || e.key === 'Enter') {
      e.preventDefault();
      toggle();
    }
  };

  let ariaAttrs: AriaAttributes = {
    'aria-checked': checked,
    'aria-label': label
  };
</script>

<div
  {...attrs}
  {...ariaAttrs}
  role="checkbox"
  tabindex="0"
  onclick={toggle}
  onkeydown={handleKeydown}
>
  {checked ? '☑' : '☐'} {label}
</div>

Best Practices

1. Extend Element Types for Custom Components

When creating wrapper components, extend the appropriate element type:

import type { HTMLButtonAttributes } from 'svelte/elements';

interface CustomButtonProps extends HTMLButtonAttributes {
  variant: 'primary' | 'secondary';
}

2. Use Specific Event Handler Types

Prefer specific event handler types over generic ones:

// Good - specific typing
const handleClick: MouseEventHandler<HTMLButtonElement> = (e) => {
  e.currentTarget // HTMLButtonElement
};

// Avoid - generic typing
const handleClick = (e: Event) => {
  (e.target as HTMLButtonElement) // requires casting
};

3. Leverage currentTarget for Type Safety

Event handlers receive currentTarget with the correct element type:

const handleInput: FormEventHandler<HTMLInputElement> = (e) => {
  const value = e.currentTarget.value; // No casting needed
  const checked = e.currentTarget.checked; // TypeScript knows this is an input
};

4. Use ARIA Attributes for Accessibility

Always include ARIA attributes when creating custom interactive elements:

let attrs: AriaAttributes & HTMLAttributes<HTMLDivElement> = {
  role: 'button',
  tabindex: 0,
  'aria-pressed': pressed,
  'aria-label': 'Custom button'
};

5. Type Snippet Parameters Properly

Use tuple types for snippet parameters:

interface Props {
  // Single parameter
  item: Snippet<[{ id: number; name: string }]>;

  // Multiple parameters
  cell: Snippet<[number, number, string]>;

  // No parameters
  header: Snippet;
}

Additional Resources

Last Updated: 2026-01-08 Svelte Version: 5.46.1