Skip to content

Events

TelInput uses callback props (not Svelte dispatched events) for state changes. All callbacks are optional.

CallbackSignatureFires when
onValueChange(value: string, details: DetailedValue | null) => voidThe E.164 value or detailed value changes
onCountryChange(country: CountryCode | null) => voidThe country is auto-detected from a dial code
onValidityChange(valid: boolean, error: ValidationError) => voidThe validity state changes
onError(error: string) => voidA parse error occurs
onLoad() => voidThe component has initialized (fires once)
<script lang="ts">
import { TelInput } from 'svelte-tel-input';
import type { DetailedValue, CountryCode, ValidationError } from 'svelte-tel-input/types';
const handleValueChange = (value: string, details: DetailedValue | null) => {
console.log('E.164:', value);
console.log('Details:', details);
};
const handleCountryChange = (country: CountryCode | null) => {
console.log('Country detected:', country);
};
const handleValidityChange = (valid: boolean, error: ValidationError) => {
console.log('Valid:', valid, 'Error:', error);
};
</script>
<TelInput
onValueChange={handleValueChange}
onCountryChange={handleCountryChange}
onValidityChange={handleValidityChange}
onError={(err) => console.error('Parse error:', err)}
onLoad={() => console.log('TelInput ready')}
/>

Both approaches work simultaneously:

  • Bindings (bind:value, bind:valid, etc.) — reactive state in the parent
  • Callbacks — side effects (logging, analytics, API calls, form submission)
<script>
let value = $state('');
let valid = $state(true);
</script>
<TelInput
bind:value
bind:valid
onValueChange={(v) => savePhoneNumber(v)}
/>

Only when the country is auto-detected from user input (e.g. typing +44 switches to GB). It does not fire when:

  • You set country programmatically via binding
  • api.reset() is called

Unlike a simple boolean callback, onValidityChange also receives the ValidationError — giving you the granular reason in one callback:

<TelInput
onValidityChange={(valid, error) => {
if (!valid && error === 'TOO_SHORT') {
showHint('Keep typing...');
}
}}
/>