Error notifications continue to appear despite the presence of data in the input field

I am utilizing a component to exhibit various information (such as first name, last name, phone number, etc.) fetched from the API. The main focus is on executing CRUD operations, particularly the update operation.
Referencing the image below:

https://i.sstatic.net/jRzQj.png

An issue arises when I click the SAVE button even though there is data in the input field(such as phone number). It continues to display warning messages (e.g., mat-error). As shown in the image below:

https://i.sstatic.net/7463t.png

Here is the code snippet for my component:

HTML

<form [formGroup]="editForm">

      <div>
        <mat-form-field>
          <input matInput placeholder="First Name" formControlName="firstname" required>
          <mat-error *ngIf="editForm.controls.firstname.hasError('required')">
            Please enter first name
          </mat-error>
        </mat-form-field>
      </div>

      <div>
        <mat-form-field class="example-full-width">
          <input matInput  placeholder="Last Name" formControlName="lastname" required>
          <mat-error *ngIf="editForm.controls.lastname.hasError('required')">
            Please enter last name
          </mat-error>
        </mat-form-field>
      </div>

      <div>
        <mat-form-field class="phone-number">
          <input matInput placeholder="Phone Number" formControlName="phonenumber" required>
          <mat-error *ngIf="editForm.controls.phonenumber.hasError('required')">
            Please enter phone number
          </mat-error>
          <mat-error *ngIf="editForm.controls.phonenumber.hasError('pattern')">
            Please enter a valid phone number
          </mat-error>
        </mat-form-field>
      </div>

      <div class="btn-sec">
        <button mat-flat-button  type="button" >Cancel</button>
        <button mat-flat-button  type="submit" (click)="onEditForm()">Save</button>
      </div>

   <form>

TS

import{ Component, Inject, Input, OnInit, ViewChild } from '@angular/core';
import{ FormBuilder, FormControl ,FormGroup, Validators}fro'@angular/forms';
import {MAT_DIALOG_DATA, MatDialog, MatDialogRef} from '@angular/material';
import {IContact } from 'src/app/models/app.models';


@Component({
  selector: 'wsd-update-customer',
  templateUrl: './wsd-customer.component.html',
  styleUrls: ['./wsd-customer.component.css'],
})

export class EditCustomerComponent implements OnInit {

 public editForm: FormGroup;

constructor(@Inject(MAT_DIALOG_DATA) public data: IContact,
          private fb: FormBuilder,
          public dialog: MatDialog) {} 

public ngOnInit(): void {
  this.editForm = this.fb.group({
    firstname: [ null, [Validators.required],
    lastname: [null, [Validators.required],
    phonenumber: [null, [Validators.required, Validators.pattern('[0-9]+')]],
   });

this.editForm.get('firstname').setValue(this.data.firstName);
this.editForm.get('lastname').setValue(this.data.lastName);
this.editForm.get('phonenumber').setValue(this.data.phoneNumbers[0].number);
}

 public onEditForm(): void {
   this.markAsDirty(this.editForm);
 }


 private markAsDirty(group: FormGroup): void {
    group.markAsDirty();
     for (const i in group.controls) {
      group.controls[i].markAsDirty();
   }
  }

}

models.ts file

export interface IContact {
  firstName:  string;
  lastName:   string;
   phoneNumbers:  IPhoneNumber[];
 }

 export interface IPhoneNumber {
  type:        string;
  number:      string;
 }

JSON

 {
    "firstName": "Adaline",
   "lastName": "Danat",
   "phoneNumbers": [
      {
        "type": "Home",
        "number": "+62 342 886 8201"
      },
      {
        "type": "Business",
        "number": "+63 704 441 1937"
      },
      {
        "type": "Unknown",
        "number": "+63 530 693 2767"
      }
   ]

}

Updated Photo

https://i.sstatic.net/XMC1l.png

Updated Stckblitz link

Answer №1

Utilizing both FormGroup and FormControl allows for efficient form handling in Angular. The FormGroup accepts an object of child controls from the AbstractControl Class.

When using FormGroup, the parameter 'controlsConfig' defines a collection of child controls with each registered under a specific name.

To implement this, define the FormGroup with FormControls while specifying validation rules and default values:

this.editForm = this.fb.group({
      firstname: new FormControl([null, [Validators.required]]),
      lastname: new FormControl([null, [Validators.required]]),
      phonenumber: new FormControl([null, [Validators.required, Validators.pattern('[0-9]+')]]),
});

EDIT:

There are various ways to display the value of a formControl outside an input field like in a p or span:

1) Using Two-way data binding directly on the data:

<p>{{data.email}}</p>

2) Utilizing the FormControl method:

<p>{{editForm.value.email}}</p>

In this case, a FormControl needs to be defined in the TS file and the value is set using setValue.

email: new FormControl([null])  //define control in group

this.editForm.get('email').setValue(this.data.email); //assign value from data object

3) Alternatively, use the FormContol along with the readonly attribute:

<mat-form-field class="example-full-width">
     <input matInput placeholder="Email" formControlName="email" readonly>
</mat-form-field>

View Working StackBlitz Example

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

What is the process of converting a union type into a union of arrays in TypeScript?

I have a Foo type that consists of multiple types For example: type Foo = string | number I need to receive this type and convert it into an array of the individual types within the union type TransformedFoo = ToUnionOfArray<Foo> // => string[] ...

Place information from an input field into a specific row within a table

Utilizing Angular 4, I am developing a frontend application for a specific project. The interface features a table with three rows that need to be filled with data from an external source. https://i.stack.imgur.com/Dg576.png Upon clicking the "aggiungi p ...

Error in TypeScript when utilizing an Enum as a string

Attempting to include a string enum in my Angular 2 project resulted in an error during the npm project startup: ERROR in e:/projects/dbtool-fullstack/dbtool-client/src/app/shared/models/full-m odels/enums/Sex.ts (2,10): Type '"Male"' is not ass ...

Is there a way to extract various pieces of data from a single object and implement them in a NextJs 13 application directory?

My Django RESTapi is providing output data in the following format: { "count": 1000, "next": "http://127.0.0.1:8000/store/products/?page=2", "previous": null, "results": [ { "id": 648, ...

Standards for coding across different languages

As I work on developing a framework that accommodates both C# and TypeScript, I am faced with an interesting dilemma. Take, for instance, the Validator class in C#: class Validator { public bool Validate(string value) { return someConditi ...

What is the process for transferring data processed in Python to Node.js and then forwarding it to Angular?

I am a newcomer to Angular and I'm looking for a way to showcase JSON data from Python in my Angular app using Node.js. I have already utilized child processes to establish the connection between Python and Node.js, but I am facing a challenge on how ...

What is the process of converting a byte array into a blob using JavaScript specifically for Angular?

When I receive an excel file from the backend as a byte array, my goal is to convert it into a blob and then save it as a file. Below is the code snippet that demonstrates how I achieve this: this.getFile().subscribe((response) => { const byteArra ...

Destructuring objects with default values from two related interfaces

In my project, I have defined two interfaces called User and BankUser. The structure of the interface for BankUser looks like this: interface BankUser extends User { banks: { [bank_id: string]: string}; isSuper: boolean; } I am working on a function ...

Looking to create an interactive audio experience for users with Angular by playing audio on their click events sourced from Firebase?

I am currently developing a dashboard where I aim to enable users to play specific audio files that they select from a table by clicking on a play button. These audio recordings are stored in Firebase storage. The issue I am facing is that when I manually ...

Typescript: Maximizing efficiency and accuracy

When it comes to developing Angular2 apps using Typescript, what are the essential best practices that we should adhere to? ...

Modify visibility within a subclass

Is there a way to modify property visibility in a child class from protected to public? Consider the following code snippet: class BaseFoo { protected foo; } class Foo extends BaseFoo { foo = 1; } new Foo().foo; It seems that this change is pos ...

The issue arises when attempting to call a method from the same service within jsPDF in an Angular environment

Below you will find my Angular project's pdfService. I am facing an issue where calling the this.formatter() method inside myPDF is not functioning properly. export class pdfService { formatter(value: number): string { return new Intl.N ...

Remove the export statement after transpiling TypeScript to JavaScript

I am new to using TypeScript. I have a project with Knockout TS, and after compiling it (using the Intellij plugin to automatically compile ts to js), this is my sample.ts file: import * as ko from "knockout"; ko; class HelloViewModel { language: Kn ...

What is the best approach to develop a React Component Library adorned with Tailwind CSS and enable the main project to easily customize its theme settings?

Currently, I am in the process of developing an internal component library that utilizes Tailwind for styling. However, a question has arisen regarding how the consuming project can incorporate its own unique styles to these components. Although I have th ...

The ngAfterContentInit lifecycle hook is not triggered when the parent component updates the child component

I am trying to understand the functionality of the ngOnChanges callback in Angular. I have implemented it to observe changes in a property annotated with the Input decorator as shown below: @Input() postsToAddToList: Post[] = []; However, after compiling ...

"Implemented a fresh pathway within the app-routing.module.ts file, but unfortunately, ngxAdmin is experiencing functionality issues

While customizing the ngx-admin template, I attempted to incorporate a new module into the app module and added its route in app-routing.module.ts. However, upon trying to open it, the module seems to be stuck at loading without any errors appearing in the ...

The Angular Date Picker stubbornly refuses to show dates in the format of DD/MM

Implementation of my Application import { MAT_MOMENT_DATE_ADAPTER_OPTIONS, MAT_MOMENT_DATE_FORMATS, MomentDateAdapter } from '@angular/material-moment-adapter'; import { MAT_FORM_FIELD_DEFAULT_OPTIONS } from '@angular/material/form-fie ...

A guide to finding the mean in Angular by utilizing JSON information

import { Component, OnInit } from "@angular/core"; import { MarkService } from "../app/services/marks.service"; @Component({ selector: "app-root", templateUrl: "./app.component.html", styleUrls: ["./app.component.scss"] }) export class AppComp ...

What is the best way to initiate the registration page through the @auth0/auth0-react library?

I've hit a roadblock in trying to automatically launch the sign-up (registration) page using @auth0/auth0-react. Previously, I would send mode which worked with auth0-js. So far, I have attempted the following without success: const { loginWithRedir ...

In ReactJS with TypeScript, declaring a constant response after calling the login function using the await keyword

Currently tackling a task in React and Typescript where I am logging in as a user. Encountering an issue when trying to access the response variable, which leads to the following error: Object is of type 'unknown'.ts(2571) const response: unknow ...