Angular响应式表单奇怪的行为

huangapple go评论86阅读模式
英文:

Angular Reactive form werid behavior

问题

以下是您提供的代码的翻译部分:

login.component.html

<div class="main">
    <div class="image">
        <img src="./assets/icons/login.png" alt="Login">
        <p>Login in to your account</p>
    </div>
    <form [formGroup]="form" class="login" (ngSubmit)="onClick()">
        <p class="error-message" style="font-size: large;" *ngIf="!isValid">请填写您的信息</p>
        <p>输入您的用户名和密码</p>
        <div class="userName">
            <label for="userName">用户名</label>
            <br>
            <input [ngClass]="{'error': emailValidation && !isValid}" type="text" id="userName" placeholder="您的用户名" formControlName="email">
            <p class="error-message" *ngIf="emailValidation && !isValid">请输入您的用户名</p>
        </div>
        <div class="pass">
            <label for="pass">密码</label>
            <br>
            <input [ngClass]="{'error': passwordValidation || !isValid}" type="password" id="pass" placeholder="您的密码" formControlName="password">
            <p class="error-message" *ngIf="passwordValidation || !isValid">请输入您的用户密码</p>
        </div>
        <button class="btnConfig" id="btnlogin"><img src="./assets/icons/login-btn.png" alt="登录"> 登录</button>
    </form>
</div>

login.component.ts:

import { AfterContentChecked, Component, DoCheck, OnChanges, OnInit, SimpleChanges } from '@angular/core';
import { FormGroup, FormBuilder, Validators } from '@angular/forms';
import { Router } from '@angular/router';

@Component({
  selector: 'app-login',
  templateUrl: './login.component.html',
  styleUrls: ['./login.component.css']
})
export class LoginComponent implements OnInit, DoCheck {
  form!: FormGroup;
  isValid: boolean = true;

  constructor (private formBuilder: FormBuilder, private router: Router) {}

  ngOnInit(): void {
    this.form = this.formBuilder.group({
      email: ['', Validators.required],
      password: ['', Validators.required]
    });

    this.form.valueChanges.subscribe()
  }

  ngDoCheck(): void {
    this.form.valueChanges.subscribe(() => {
      this.isValid = this.form.valid;
    });  
  }

  get emailValidation() {
    return this.form.get('email')?.invalid || this.form.get('email')?.touched;
  }

  get passwordValidation() {
    return this.form.get('password')?.invalid && this.form.get('password')?.touched;
  }

  onClick() {
    if(this.form.valid) {
      this.router.navigate(['/dashboard']);
    } else {
      this.isValid = this.form.valid;
    }
  }
}

请注意,我已对其中的HTML和TypeScript代码进行了翻译,但没有包括代码中的注释和描述。如果您需要更多帮助或有其他问题,请随时提出。

英文:

i have this code i'm working on:

login.component.html

&lt;div class=&quot;main&quot;&gt;
&lt;div class=&quot;image&quot;&gt;
&lt;img src=&quot;./assets/icons/login.png&quot; alt=&quot;Login&quot;&gt;
&lt;p&gt;Login in to your account&lt;/p&gt;
&lt;/div&gt;
&lt;form [formGroup]=&quot;form&quot; class=&quot;login&quot; (ngSubmit)=&quot;onClick()&quot;&gt;
&lt;p class=&quot;error-message&quot; style=&quot;font-size: large;&quot; *ngIf=&quot;!isValid&quot;&gt;Please fill the your info&lt;/p&gt;
&lt;p&gt;Enter your user name and password&lt;/p&gt;
&lt;div class=&quot;userName&quot;&gt;
&lt;label for=&quot;userName&quot;&gt;User name&lt;/label&gt;
&lt;br&gt;
&lt;input [ngClass]=&quot;{&#39;error&#39;: emailValidation &amp;&amp; !isValid}&quot; type=&quot;text&quot; id=&quot;userName&quot; placeholder=&quot;Your user name&quot; formControlName=&quot;email&quot;&gt;
&lt;p class=&quot;error-message&quot; *ngIf=&quot;emailValidation &amp;&amp; !isValid&quot;&gt;please enter your user name&lt;/p&gt;
&lt;/div&gt;
&lt;div class=&quot;pass&quot;&gt;
&lt;label for=&quot;pass&quot;&gt;Password&lt;/label&gt;
&lt;br&gt;
&lt;input [ngClass]=&quot;{&#39;error&#39;: passwordValidation || !isValid}&quot; type=&quot;password&quot; id=&quot;pass&quot; placeholder=&quot;your password&quot; formControlName=&quot;password&quot;&gt;
&lt;p class=&quot;error-message&quot; *ngIf=&quot;passwordValidation || !isValid&quot;&gt;please enter your user password&lt;/p&gt;
&lt;/div&gt;
&lt;button class=&quot;btnConfig&quot; id=&quot;btnlogin&quot;&gt;&lt;img src=&quot;./assets/icons/login-btn.png&quot; alt=&quot;login&quot;&gt; Login&lt;/button&gt;
&lt;/form&gt;             
&lt;/div&gt;

login.component.ts:

import { AfterContentChecked, Component, DoCheck, OnChanges, OnInit, SimpleChanges } from &#39;@angular/core&#39;;
import { FormGroup, FormBuilder, Validators } from &#39;@angular/forms&#39;;
import {  Router } from &#39;@angular/router&#39;;
@Component({
selector: &#39;app-login&#39;,
templateUrl: &#39;./login.component.html&#39;,
styleUrls: [&#39;./login.component.css&#39;]
})
export class LoginComponent implements OnInit, DoCheck {
form!: FormGroup;
isValid: boolean = true;
constructor (private formBuilder: FormBuilder, private router: Router) {}
ngOnInit(): void {
this.form = this.formBuilder.group({
email: [&#39;&#39;, Validators.required],
password: [&#39;&#39;, Validators.required]
});
this.form.valueChanges.subscribe()
}
ngDoCheck(): void {
this.form.valueChanges.subscribe(() =&gt; {
this.isValid = this.form.valid;
});  
}
get emailValidation() {
return this.form.get(&#39;email&#39;)?.invalid || this.form.get(&#39;email&#39;)?.touched;
}
get passwordValidation() {
return this.form.get(&#39;password&#39;)?.invalid &amp;&amp; this.form.get(&#39;password&#39;)?.touched;
}
onClick() {
if(this.form.valid) {
this.router.navigate([&#39;/dashboard&#39;]);
} else {
this.isValid = this.form.valid;
}
}
}

Live preview

ever thing work fine with the validation until i press the login button with the two input fields empty the error message show and when i just fill one of the input the error messages disappear from both fields

i tried

ngDoCheck(): void {
this.form.valueChanges.subscribe(() =&gt; {
this.isValid = this.form.valid;
});  
}

to keep checking but still the bug doesn't go

答案1

得分: 0

login.component.ts:

我通过移除 ngDoCheck,将订阅移到 ngOnInit 中,替换 isVaild  isSubmitted,编辑 passwordValidation  emailValidation,以及将 OnClick 编辑为 onSubmit 来解决了这个问题。

login.component.ts

login.component.html:

login.component.html:
英文:

i fix the problem by remove the ngDoCheck, put the subscription in to ngOnInit,
replace the isVaild with isSubmitted, edit the passwordValidation and emailValidation, and edit the OnClick to be onSubmit

login.component.ts:

    import { AfterContentChecked, Component, DoCheck, OnChanges, OnInit, SimpleChanges } from &#39;@angular/core&#39;;
import { FormGroup, FormBuilder, Validators } from &#39;@angular/forms&#39;;
import {  Router } from &#39;@angular/router&#39;;
@Component({
selector: &#39;app-login&#39;,
templateUrl: &#39;./login.component.html&#39;,
styleUrls: [&#39;./login.component.css&#39;]
})
export class LoginComponent implements OnInit {
form!: FormGroup;
isSubmitted: boolean = false;
constructor (private formBuilder: FormBuilder, private router: Router) {}
ngOnInit(): void {
this.form = this.formBuilder.group({
email: [&#39;&#39;, Validators.required],
password: [&#39;&#39;, Validators.required]
});
this.form.valueChanges.subscribe()
}
get emailValidation() {
return this.form.get(&#39;email&#39;)?.invalid &amp;&amp; (this.form.get(&#39;email&#39;)?.dirty || this.form.get(&#39;email&#39;)?.touched || this.isSubmitted);
}
get passwordValidation() {
return this.form.get(&#39;password&#39;)?.invalid &amp;&amp; (this.form.get(&#39;password&#39;)?.dirty || this.form.get(&#39;password&#39;)?.touched || this.isSubmitted);
}
onSubmit(): void {
if(this.form.valid){
this.router.navigate([&#39;/dashboard&#39;])
}
this.isSubmitted = true;
}
}

login.component.html:

&lt;div class=&quot;main&quot;&gt;
&lt;div class=&quot;image&quot;&gt;
&lt;img src=&quot;./assets/icons/login.png&quot; alt=&quot;Login&quot;&gt;
&lt;p&gt;Login in to your account&lt;/p&gt;
&lt;/div&gt;
&lt;form [formGroup]=&quot;form&quot; class=&quot;login&quot; (ngSubmit)=&quot;onSubmit()&quot;&gt;
&lt;p class=&quot;error-message&quot; style=&quot;font-size: large;&quot; *ngIf=&quot;isSubmitted&quot;&gt;Please fill the your info&lt;/p&gt;
&lt;p&gt;Enter your user name and password&lt;/p&gt;
&lt;div class=&quot;userName&quot;&gt;
&lt;label for=&quot;userName&quot;&gt;User name&lt;/label&gt;
&lt;br&gt;
&lt;input [ngClass]=&quot;{&#39;error&#39;: emailValidation}&quot; type=&quot;text&quot; id=&quot;userName&quot; placeholder=&quot;Your user name&quot; formControlName=&quot;email&quot;&gt;
&lt;p class=&quot;error-message&quot; *ngIf=&quot;emailValidation&quot;&gt;please enter your user name&lt;/p&gt;
&lt;/div&gt;
&lt;div class=&quot;pass&quot;&gt;
&lt;label for=&quot;pass&quot;&gt;Password&lt;/label&gt;
&lt;br&gt;
&lt;input [ngClass]=&quot;{&#39;error&#39;: passwordValidation}&quot; type=&quot;password&quot; id=&quot;pass&quot; placeholder=&quot;your password&quot; formControlName=&quot;password&quot;&gt;
&lt;p class=&quot;error-message&quot; *ngIf=&quot;passwordValidation&quot;&gt;please enter your user password&lt;/p&gt;
&lt;/div&gt;
&lt;button class=&quot;btnConfig&quot; id=&quot;btnlogin&quot; type=&quot;submit&quot;&gt;&lt;img src=&quot;./assets/icons/login-btn.png&quot; alt=&quot;login&quot;&gt; Login&lt;/button&gt;
&lt;/form&gt;             
&lt;/div&gt;

huangapple
  • 本文由 发表于 2023年4月17日 17:14:44
  • 转载请务必保留本文链接:https://go.coder-hub.com/76033515.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定