简体   繁体   English

是否有一个生命周期钩子在组件初始化后运行一次,但是在加载双向绑定之后?

[英]Is there a lifecycle hook that runs once after a components initialisation, but also after two-way-binding is loaded?

I am trying to select some text in an input field after a component is initialised. 我正在尝试在初始化组件后在输入字段中选择一些文本。 I know I can do this with a setTimeout() , but that feels a bit too hacky. 我知道我可以用setTimeout()做到这一点,但感觉有点过于hacky。

Most hooks run before the input text is loaded by two-way binding. 大多数钩子在输入文本通过双向绑定加载之前运行。 The others also run every time someone selects the other field. 每当有人选择其他字段时,其他人也会运行。

The code: https://stackblitz.com/edit/angular-pxrssq 代码: https//stackblitz.com/edit/angular-pxrssq

import { Component, OnInit, Input, ViewChild } from '@angular/core';

@Component({
  selector: 'app-child',
  template: `
    <input #input type="text" [(ngModel)]="info.one"/>
    <input type="text" [(ngModel)]="info.two"/>`,
  styleUrls: ['./child.component.css']
})
export class ChildComponent implements OnInit {
  @Input() info;
  @ViewChild('input', {static: true} ) input;

  constructor() { }

  ngOnInit() {
    this.input.nativeElement.select();
  }

}

Is there a lifecycle hook that runs once after a components initialisation, but after two-way-binding is loaded? 是否有一个生命周期钩子在组件初始化后运行一次,但在加载双向绑定后?

as a matter of fact, using setTimeout() is not a hacky solution it is the solution. 作为事实上,使用setTimeout() 不是哈克溶液解决方案。 because of angular's unidirectional data flow rule . 因为angular的单向数据流规则

Angular's unidirectional data flow rule forbids updates to the view after it has been composed. Angular的单向数据流规则禁止在编写视图后对视图进行更新。

in order to observe consequences of this rule, try assigning a new value to info property of ChildComponent on AfterViewInit hook. 为了遵守这一规则的后果,尝试分配一个新的价值, info的财产ChildComponentAfterViewInit钩。 you'll get an ExpressionChangedAfterItHasBeenCheckedError which is angular's way of saying that "updates to the view after it has been composed is forbidden!" 你会得到一个ExpressionChangedAfterItHasBeenCheckedError ,这是一种角度的说法,“禁止在视频编写后对视图进行更新!”

since you are not updating any of your component's data-bound properties and just making dom manipulation, angular is not throwing any error but it is not reflecting your changes to dom as well. 由于您没有更新任何组件的数据绑定属性并且只是进行dom操作,因此angular不会抛出任何错误,但它也不会反映您对dom的更改。

coming back to your question; 回到你的问题;

Is there a lifecycle hook that runs once after a components initialisation, but after two-way-binding is loaded? 是否有一个生命周期钩子在组件初始化后运行一次,但在加载双向绑定后?

yes there is and it is AfterViewInit hook. 是的,它是AfterViewInit钩子。 Because; 因为;

View queries are set before the ngAfterViewInit callback is called. 在调用ngAfterViewInit回调之前设置视图查询。

and DOM updates are handled before ngAfterViewInit is called as explained in here . 和之前DOM更新处理ngAfterViewInit被称为中说明这里

and it comes after OnChanges hook, where; 而谈到 OnChanges钩,在这里;

OnChanges is called when any data-bound property of a directive changes. 当指令的任何数据绑定属性更改时,将调用OnChanges。

consequently you should do as follows if you want the text get selected just once when the first time component is loaded. 因此,如果您希望在加载第一个时间组件时仅选择一次文本,则应执行以下操作。

ngAfterViewInit() {
  setTimeout(() => this.input.nativeElement.select());
}

if you want to select text whenever input property gets changed by parent component (including first load) then you need to implement OnChanges hook. 如果要在父组件(包括第一次加载)更改input属性时选择文本,则需要实现OnChanges挂钩。

ngOnChanges() {
  setTimeout(() => this.input.nativeElement.select());
}

here is a working demo https://stackblitz.com/edit/angular-owahps 这是一个工作演示https://stackblitz.com/edit/angular-owahps

hope it helps. 希望能帮助到你。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM