skip to Main Content

I’m using the ngx-intl-tel-input library in my Angular project to handle phone number input fields. I’ve created a reusable component for the phone number field, and I am passing a FormControl from the parent component to it.

Here is my code:

component.ts

import { Component, Input } from '@angular/core';
import { FormControl } from '@angular/forms';
import { CountryISO, PhoneNumberFormat, SearchCountryField } from 'ngx-intl-tel-input';

@Component({
  selector: 'app-new-phone-no-field-v1',
  templateUrl: './new-phone-no-field-v1.component.html',
  styleUrl: './new-phone-no-field-v1.component.css'
})
export class NewPhoneNoFieldV1Component {
  @Input() control!: FormControl;
  @Input() separateDialCode: boolean = false;
  @Input() maxLength: number = 15;
  @Input() phoneValidation: boolean = true;

  preferredCountries: CountryISO[] = [
    CountryISO.UnitedStates,
    CountryISO.UnitedKingdom,
    CountryISO.India,
    CountryISO.Australia,
    CountryISO.Philippines,
    CountryISO.Thailand,
    CountryISO.SouthAfrica,
    CountryISO.Panama,
    CountryISO.Mexico,
    CountryISO.Indonesia,
    CountryISO.Canada,
    CountryISO.DominicanRepublic,
  ];
  searchCountryField: SearchCountryField[] = [
    SearchCountryField.Iso2,
    SearchCountryField.Name
  ];
  phoneNumberFormat: PhoneNumberFormat = PhoneNumberFormat.National;
  selectedCountryISO: CountryISO = CountryISO.UnitedStates;
}

Component.html

<div class="intl-tel-input-wrapper">
    <ngx-intl-tel-input
      [cssClass]="'custom'"
      [onlyCountries]="preferredCountries"
      [enableAutoCountrySelect]="true"
      [enablePlaceholder]="true"
      [searchCountryFlag]="true"
      [searchCountryField]="searchCountryField"
      [selectFirstCountry]="false"
      [selectedCountryISO]="selectedCountryISO"
      [maxLength]="maxLength"
      [phoneValidation]="phoneValidation"
      [separateDialCode]="true"
      [numberFormat]="phoneNumberFormat"
      name="phone"
      [formControl]="control">
    </ngx-intl-tel-input>
    <div *ngIf="control.touched && control.invalid" class="error-messages">
      <div *ngIf="control.errors?.required">Phone number is required.</div>
      <div *ngIf="!control.errors?.validatePhoneNumber?.valid">Invalid phone number.</div>
    </div>
  </div>
  

Parent.component.html

<app-new-phone-no-field-v1 
  [control]="$any(userForm.get('phone'))"
  [separateDialCode]="true">
</app-new-phone-no-field-v1>

<div class="error error-msg">
  <div *ngIf="f.phone.errors?.required">
    Phone Number is required.
  </div>
  <div *ngIf="f.phone.errors?.pattern">
    Phone Number is invalid.
  </div>
</div>

API Data:
The API returns phone numbers in the format: +919876543210. I’m patching this data to the form using:

this.userForm.patchValue({ phone: data.phone });

Issues:

  • On the UI, the country code appears twice: once in the dial code
    dropdown and again in the phone number field. Example: +91 appears in
    the dropdown and +919876543210 appears in the input field.

  • The phone number is not formatted automatically based on the selected
    country. Example: When I select the US as the country, it doesn’t
    format the number as (201)-555-1234.

Attempts:

  • I’ve tried setting the value property of the FormControl explicitly.
  • Ensured ngx-intl-tel-input configuration matches the documentation.

How can I fix these issues so that:

  • The country code does not appear twice.
  • The phone number is automatically formatted based on the selected country?
    Any guidance would be appreciated!

Image1

Image2

2

Answers


  1. Try setting up PhoneNumberFormat to E164. Also a working stackblitz will help debug and provide a quick solution to it.

    Login or Signup to reply.
  2. So you’re getting the country code as part of the phone number from API, and you also have separate dial code displayed? Then it seems to me that you have to force the plugin to re-handle the data you patch it, since it won’t do it on its own:

    • patch the form with the value as you are already doing,
    • the plugin will generate the nationalNumber (like (201)-555-1234) and dialCode (like +1) values based on its own handling of the input value,
    • patch the form with the nationalNumber value: it will now display the format you want with the stripped country code.

    Something like:

    evilPluginPusher(dataPhone:string) { // call it by passing your data.phone value
       this.userForm.controls['phone'].patchValue(dataPhone); 
       this.userForm.updateValueAndValidity();
       setTimeout(() => {
          let formatedNumber = this.userForm.controls['phone'].value.nationalNumber;
          this.userForm.controls['phone'].patchValue(formatedNumber);
          this.userForm.updateValueAndValidity();
       }, 1); // any duration over 0
    }
    

    Yeah it has a setTimeout, so in a split second you’ll see the default value/country in the input. You can always use css to hide the element and use some var flag to trigger displaying the element when final patch has been done. The form just has to be there to be patched, and the plugin has to do its thing to get the nationalNumber, so no use in putting the whole element into ngIf.

    Stackblitz example here (I’ve put 3 different national numbers to test with).

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search