I'm starting with Angular and I'm on a project where I have to validate the inputs so they can't be left clear, every input must me completed.
It's an html and we have a .ts file.
This is an extract of the html:
<div class="form-group">
<input type="text"
class="form-control"
id="factory"
[(ngModel)]="factory.company">
</div>
I need to validate this factory input but when I was watching tutorials all I needed to do was to write 'required' inside the <input> and that was it but I had a <form> and every input was inside this form, and this html doesn't have a <form> and when I put one the design was horrible and I couldn't work.
Here is an example using required fields (in login page) :
<form [formGroup]='loginForm' (submit)="login(loginForm.value)">
<div class="col-md-6">
<div class="login-mail">
<input type="text" placeholder="Email" formControlName="email" required="">
<i class="fa fa-envelope"></i>
</div>
<div class="login-mail">
<input type="password" placeholder="Password" formControlName="password" pattern=".{8,20}" required="">
<i class="fa fa-lock"></i>
</div>
</div>
<div class="col-md-6 login-do">
<label class="hvr-shutter-in-horizontal login-sub">
<input type="submit" value="login" >
</label>
</div>
<div class="clearfix"> </div>
</form>
in the login.component.ts , u should make some changes:
1) import some modules :
import { FormBuilder, FormGroup, Validators} from '#angular/forms';
2) in oninit function :
loginForm: FormGroup;
constructor(private fb : FormBuilder) {}
ngOnInit(){
this.loginForm = this.fb.group({
email : ["", Validators.required],
password : ["", Validators.required]
});
}
Hope that helps u :)
I would think that you should be able to add a form element. However, if you cannot as you have said then you can add the ngForm directive onto any element to achieve the same behavior as having the form element.
See this plunker for examples using ReactiveFormsModule and FormsModule:
Plunker
//our root app component
import {Component, OnInit, NgModule} from '#angular/core'
import {ReactiveFormsModule, FormsModule, FormControl, Validators} from '#angular/forms'
import {BrowserModule} from '#angular/platform-browser'
#Component({
selector: 'my-app',
template: `
<div>
<h2>Hello {{name}}</h2>
<div class="form-group">
<label>Model Driven Form</label>
<input type="text"
class="form-control"
id="companyModel"
[formControl]="companyModel">
<span [hidden]="companyModel.valid || companyModel.pristine">REQUIRED!</span>
</div>
<div class="form-group" ngForm #myForm="ngForm">
<label>Template Driven Form</label>
<input type="text"
class="form-control"
name="companyTemplate"
ngModel
id="companyTemplate"
#companyTemplate="ngModel"
required>
<span [hidden]="companyTemplate.valid || companyTemplate.pristine">REQUIRED!</span>
</div>
</div>
`,
})
export class App implements OnInit {
name:string;
companyModel: FormControl
constructor() {
this.name = 'Form Validation Demo'
}
ngOnInit() {
this.companyModel = new FormControl('', Validators.required)
}
}
#NgModule({
imports: [ BrowserModule, ReactiveFormsModule, FormsModule ],
declarations: [ App ],
bootstrap: [ App ]
})
export class AppModule {}
Related
I was trying to build an angular library for custom validator directive which can validate confirm password but as i build that library and publish on local npm and imported in my project it is throwing ERROR TypeError: tView is null error. here is codes
src\lib\confirm-password-validation.directive.ts
import { Directive } from '#angular/core';
import { FormGroup, NG_VALIDATORS, ValidationErrors, Validator } from '#angular/forms';
#Directive({
selector: '[appConfirmPasswordValidation]',
providers:[{
provide:NG_VALIDATORS,
useClass:ConfirmPasswordValidationDirective,
multi:true
}]
})
export class ConfirmPasswordValidationDirective {
constructor() {
console.log('Form Directive')
}
validate(form:FormGroup|any): ValidationErrors | null {
if(!form.controls.password || !form.controls.confirmPassword){
return null;
}
if(form.controls.password.errors && form.controls.confirmPassword.errors){
return null;
}
if(form.controls.password.value !== form.controls.confirmPassword.value){
form.controls.confirmPassword.setErrors({matchPassword:true});
return {matchPassword:true}
}
return null;
}
}
src\lib\confirm-password-validation.module.ts
import { NgModule } from '#angular/core';
import { ConfirmPasswordValidationComponent } from './confirm-password-validation.component';
import { ConfirmPasswordValidationDirective } from './confirm-password-validation.directive';
#NgModule({
declarations: [
ConfirmPasswordValidationComponent,
ConfirmPasswordValidationDirective
],
imports: [],
exports: [
ConfirmPasswordValidationComponent,
ConfirmPasswordValidationDirective
]
})
export class ConfirmPasswordValidationModule { }
src\public-api.ts
/*
* Public API Surface of confirm-password-validation
*/
export * from './lib/confirm-password-validation.service';
export * from './lib/confirm-password-validation.component';
export * from './lib/confirm-password-validation.module';
export * from './lib/confirm-password-validation.directive';
After publish i have installed in my project
src\app\app.module.ts
import { NgModule } from '#angular/core';
import { FormsModule, ReactiveFormsModule } from '#angular/forms';
import { BrowserModule } from '#angular/platform-browser';
import { ConfirmPasswordValidationModule } from 'confirm-password-validation';
import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
#NgModule({
declarations: [
AppComponent,
],
imports: [
BrowserModule,
AppRoutingModule,
FormsModule,
ReactiveFormsModule,
ConfirmPasswordValidationModule,
],
providers: [],
bootstrap: [AppComponent]
})
export class AppModule { }
src\app\app.component.html
<div class="w-100 d-flex justify-content-center align-items-center" style="height: 100vh;">
<div class="card p-5">
<form [formGroup]="userForm" (ngSubmit)="submit()" appConfirmPasswordValidation>
<div class="mb-3 mt-3">
<label for="email" class="form-label">Email:</label>
<input type="email" class="form-control" id="email" placeholder="Enter email" formControlName="email">
</div>
<div class="mb-3">
<label for="pwd" class="form-label">Password:</label>
<input type="password" class="form-control" placeholder="Enter password" formControlName="password">
</div>
<div class="mb-3">
<label for="pwd" class="form-label">Confirm Password:</label>
<input type="password" class="form-control" placeholder="Enter password" formControlName="confirmPassword">
<p>
<span *ngIf="confirmPassword?.hasError('matchPassword')">
Password Mismatch
</span>
</p>
</div>
<div class="form-check mb-3">
<label class="form-check-label">
<input class="form-check-input" type="checkbox" name="remember"> Remember me
</label>
</div>
<button type="submit" class="btn btn-primary">Submit</button>
</form>
</div>
</div>
ERROR
I have written a registration page component in Angular. I have followed what few tutorials there are and I have stumbled upon a very frustrating bug. Pressing the submit button on the form will simply cause the console to print out "undefined" when trying to access the NgForm's value. Accessing the "valid" field of the NgForm will return true or false, as expected.
the page:
<app-players></app-players>
<div class="container" style="text-align:center">
<h3>Register a new account!</h3>
<form #f="ngForm" (ngSubmit)="onSubmit(f)">
<label>Username:</label> <input type="text" id="username"
required #username="ngModel"
name="username" ngModel><br>
<label>Password:</label> <input type="password" id="password"
required #password="ngModel"
name="password" ngModel><br>
<label>Email:</label> <input type="text" id="email"
required #email="ngModel"
name="email" ngModel><br>
<button type="submit" class="btn btn-success" [disabled]="!newPlayerEntry.form.valid">Submit</button>
</form>
</div>
<div id = "result">
</div>
The component:
import { Component, OnInit } from '#angular/core';
import { NgForm } from '#angular/forms';
import { NewPlayer } from './new-player';
#Component({
selector: 'app-players-register',
templateUrl: './players-register.component.html',
styleUrls: ['./players-register.component.css']
})
export class PlayersRegisterComponent implements OnInit {
constructor() {
}
ngOnInit() {
}
onSubmit(f: NgForm) {
console.log(f.value);
}
}
You need remove [disabled]="!newPlayerEntry.form.valid" and change to [disabled]="!f.valid"
This is working version
https://stackblitz.com/edit/angular-mgmmsq?file=src%2Fapp%2Fapp.component.html
I'm working on angular 5 Reactive Forms :
I had this error :
There is no directive with "exportAs" set to "ngModel"
I saw in others forums that problem can be for many reasons :
misspelling in the HTML template , forgetting to import "FormsModule" or "ReactiveFormsModule", ....
I checked my code but i didn't find the issue
Can you Help me please !!!
Console error :
There is no directive with "exportAs" set to "ngModel" ("
[(ngModel)]="user.FirstName"
formControlName="FirstName"
[ERROR ->]#FirstName="ngModel" />
<label for="firstName">{{ 'FIRST_NAME' | translate:param}}</label>")
: ng:///AppModule/LoginComponent.html#12:15
app.module.ts:
//angular moudel
import { NgModule } from '#angular/core';
import { FormsModule, ReactiveFormsModule } from '#angular/forms';
....
#NgModule({
declarations: [
.....
],
imports: [
BrowserModule,
FormsModule,
ReactiveFormsModule,
...
AppRoutingMoudel,
],
...
})
LoginComponent.ts
import { Component, OnInit } from '#angular/core';
import { User } from './../../../model/user';
import {FormBuilder,FormGroup,FormControl,Validators,NgForm} from '#angular/forms'
....
export class LoginComponent implements OnInit {
user : User;
userLoginForm: FormGroup;
constructor(private userLoginFormBuilder:FormBuilder) {
this.user = new User ("TestName", "Yagmi",
"TestName#Yagmi.com", "esay", "esay");
this.userLoginForm = this.userLoginFormBuilder.group({
FirstName: new FormControl (this.user.FirstName,
[Validators.minLength(4),])
});
}
}
LoginComponent.Html
<form class="col s12" [formGroup]="userLoginForm" (ngSubmit)="saveUserLogin()">
<div class="row">
<div class="input-field col s12 m6">
<input id="firstName"
type="text"
class="validate"
[(ngModel)]="user.FirstName"
formControlName="FirstName"
#FirstName="ngModel" />
<label for="firstName">{{ 'FIRST_NAME' | translate:param }}</label>
<p class="data-error data-validation" *ngIf="FirstName.errors?.minlength">
min length is 4 caracters.
</p>
<p class="data-error data-validation" *ngIf="FirstName?.touched">
touched.
</p>
</div>
</div>
</form>
user.ts
export class User {
constructor(
public FirstName: string,
public LastName: string,
public Email: string,
public Passeword: string,
public ConfirmPasseword: string
)
}
I find where is my error I used template driven and reactive forms together
this why i had error (after i read the comment of Alex )
the solution is just to remove all template driven from my Html template
<form class="col s12" [formGroup]="userLoginForm" (ngSubmit)="saveUserLogin()">
<div class="row">
<div class="input-field col s12 m6">
<input id="firstName"
type="text"
class="validate"
//[(ngModel)]="user.FirstName" ==> to remove template driven
formControlName="FirstName" //==> to keep reactive forms
// #FirstName="ngModel" ===> to remove template driven
/>
<label for="firstName">{{ 'FIRST_NAME' | translate:param }}</label>
<p class="data-error data-validation" *ngIf="FirstName.errors?.minlength">
min length is 4 caracters.
</p>
<p class="data-error data-validation" *ngIf="FirstName?.touched">
touched.
</p>
</div>
</div>
</form>
also im my
LoginComponent.ts
import {FormBuilder,FormGroup,FormControl,Validators} from '#angular/forms'
==> remove import NgForm no need with reactive forms
In the line
#FirstName="ngModel"
The component referenced needs to have defined "exportAs" value.
For example
#Directive({
selector: '[tooltip]',
exportAs: 'tooltip'
})
#FirstName="tooltip"
https://netbasal.com/angular-2-take-advantage-of-the-exportas-property-81374ce24d26
I am new to angular and trying to implement a reactive form. Below is my html code and TS code
<form [formGroup]="signupForm" (ngSubmit)="onSubmit()">
<div class="form-group">
<label for="email">Mail</label>
<input type="email" name="email" id="email" formControlName="email" class="form-control">
</div>
<div class="btn btn-primary" type="submit">Sign Up</div>
</form>
Here is my TS file
import { Component , OnInit} from '#angular/core';
import {FormControl, FormGroup, Validators} from '#angular/forms';
#Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent implements OnInit{
title = 'app works!';
signupForm : FormGroup;
ngOnInit(){
this.signupForm = new FormGroup({
'email' : new FormControl('test#test.com')
});
// this.signupForm.valueChanges.subscribe(
// (value) => console.log(value)
// );
}
onSubmit(){
console.log(this.signupForm);
}
}
For some reason I cannot print anything on console which I am trying to do in OnSubmit method. I checked everything and it looked okay , but still nothing comes on console when I press the button.
Can anyone please help me what am I doing wrong ?
Attribute type is not a valid type on div element. This this case you will need to have an input or button with type submit for the callback to be triggered.
<form [formGroup]="signupForm" (ngSubmit)="onSubmit()">
<div class="form-group">
<label for="email">Mail</label>
<input type="email"
name="email"
id="email"
formControlName="email"
class="form-control">
</div>
<button class="btn btn-primary" type="submit">Sign Up</button>
</form>
I am getting the following error on browser console after clicking on Submit button.
In this application I am trying to get information about the Student uploaded code below.
I am unable to find why this error is shown on console.
I have correctly added the formControlName.
Component
import { Component, OnInit, Inject } from '#angular/core';
import { FormGroup, FormControl, Validators, FormBuilder, AbstractControl } from '#angular/forms';
#Component({
selector: 'app-new-record',
templateUrl: './new-record.component.html',
styleUrls: ['./new-record.component.css']
})
export class NewRecordComponent implements OnInit {
myFormGroup: FormGroup;
constructor(private formBuilder: FormBuilder) {
this.myFormGroup = this.formBuilder.group({
name: new FormControl('', Validators.compose([
Validators.required
])),
claz: new FormControl('BCA'),
admissionYear: new FormControl(Validators.compose([Validators.required]))
});
}
ngOnInit() {
}
onSubmit(student) {
console.log('onSubmit called !');
}
}
Template
<form [formGroup]="myFormGroup"
(ngSubmit)="onSubmit(form.value)">
<div class="form-group">
<label for="claz">Class:</label> <select name="claz" formControlName="claz">
<option value="MCA">MCA</option>
<option value="BCA">BCA</option>
<option value="M.Sc">M.Sc</option>
<option value="B.Tech">B.Tech</option>
</select>
</div>
<div class="form-group">
<label for="name">Name:</label> <input type="text"
class="form-control" id="name" formControlName="name">
</div>
<div class="form-group">
<label for="admissionYear">Admission Year:</label> <input type="number"
class="form-control" id="admissionYear" formControlName="admissionYear">
</div>
<button type="submit" class="btn btn-default" >Submit</button>
</form>
There is no form defined, instead use myFormGroup which has been defined as formGroup
(ngSubmit)="onSubmit(myFormGroup.value)"