angular中使用viewchild访问DOM、子组件和指令的学习

angular中的viewchild提供了访问从组件中访问模板中书写的DOM、子组件和指令的功能。

0. 基础知识

ViewChild

Property decorator that configures a view query. The change detector looks for the first element or the directive matching the selector in the view DOM. If the view DOM changes, and a new child matches the selector, the property is updated.


View queries are set before the ngAfterViewInit callback is called.
Metadata Properties:
selector - the directive type or the name used for querying.
read - read a different token from the queried elements.

相关钩子
钩子Purpose and Timing
ngAfterViewInit()Respond after Angular initializes the component’s views and child views / the view that a directive is in.

1. 访问DOM

DOM毕竟是前端的基础,在组件中怎么访问模板中写的DOM元素呢?
假如有个组件,OneComponent,他的模板中有个input标签,如下所示:

<input type="text">

如果在模板中的另外一个地方访问这个input,可以使用local variable,修改代码如下:

<input type="text" #inputText>

但是local variable到不了组件中,希望能在组件中访问inputText 。
原生的js中有个方法叫做element.querySelector, angular中有个ViewChild装饰器。

// inputText 作为参数, the name used for querying.
  @ViewChild('inputText') inputElement: ElementRef;
  ngAfterViewInit() {
      console.log('我是原生元素哦', this.inputElement.nativeElement);
}

执行结果:
这里写图片描述

对于this.inputElement.nativeElement,这就是一个原生的DOM节点了。

2. 访问子组件

父组件通过使用子组件的selector在父组件的模板中使用子组件,就像是一个DOM元素的标签那样子。

定义一个子组件,就叫做TwoComponent吧,上面有个方法,主要代码如下:

@Component({
  template: `<br>我是子组件。`,
  selector: 'two-component'
})
export class TwoComponent {
  .
  .
  .
  sayName() {
    console.log('我是子组件');
  }
}

父组件的模板中:

<two-component #twocpt></two-component>

其中使用了本地变量,如此一来,至少父组件中至少有两种方法访问到子组件,

selector --- the directive type or the name used for querying.

一个是根据directive type,一个是根据the name 。

2.1 使用type访问子组件
@ViewChild(TwoComponent) ziComponent: TwoComponent;

// ngAfterViewInit 钩子中加入:
console.log('我是TwoComponent', this.ziComponent);
2.2 使用name访问子组件
@ViewChild('twocpt') twocomponent: TwoComponent;

//钩子ngAfterViewInit中加入:
this.twocomponent.sayName();
console.log(`this.ziComponent === this.twocomponent ? : `, this.ziComponent === this.twocomponent);

这里写图片描述

2.3 访问子组件中的DOM

ViewChild中的选择器可以传递第二个参数,

  @ViewChild(TwoComponent, {read: ElementRef}) ziComponentEle: ElementRef;

这样就可以在父组件中访问到子组件的模板中的DOM元素,不过我们直接得到的是用ElementRef封装过的元素,通过其中的属性可以进一步得到元素DOM元素。

    console.log('ziComponentEle:', this.ziComponentEle);
    console.log('ziComponentEle.nativeElement:', this.ziComponentEle.nativeElement);
    console.log('ziComponentEle.nativeElement.querySelector(\'div\'):', this.ziComponentEle.nativeElement.querySelector('div'));

这里写图片描述

3. 访问指令

写一个给input输入框赋值的指令,添加到父组件的模板的input中,

@Directive({
  selector: '[appThreeDirective]'
})
export class ThreeDirective {
  constructor(ele: ElementRef) {
    ele.nativeElement.value = '我是指令赋值';
  }

  get directiveName() {
    return '指令名';
  }
}
<input type="text" #inputText appThreeDirective>

在父组件中通过指定类型来访问这个指令:

  @ViewChild(ThreeDirective) triDirective: ThreeDirective;
  // 钩子中加入:
  console.log('我是指令名字', this.triDirective.directiveName);

这里写图片描述

参考文献:
https://alligator.io/angular/viewchild-access-component/

  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值