Angular 角度7+;,调用子组件';父母的方法是什么?

Angular 角度7+;,调用子组件';父母的方法是什么?,angular,angular7,Angular,Angular7,有时我想从父组件调用子组件的方法,或者以某种方式通知子组件(从父组件)调用某些东西 1st(从父级调用子组件的方法): // CHILD @Component({ selector: 'child-component', template: '<p>child</p>' }) class ChildComponent { doSomething() { console.log('I am from child') } } // PARENT

有时我想从父组件调用子组件的方法,或者以某种方式通知子组件(从父组件)调用某些东西

1st(从父级调用子组件的方法):

// CHILD
@Component({
  selector: 'child-component',
  template: '<p>child</p>'
})

class ChildComponent {

  doSomething() {
    console.log('I am from child')
  }

}

// PARENT
@Component({
  selector: 'parent-component',
  template: '<child-component></child-component>',
})

class ParentComponent{

  @ViewChild(ChildComponent ) child: ChildComponent;

  ngAfterViewInit() {
    this.child.doSomething();
  }
}
//CHILD
export class ChildComponent implements OnInit {

  @Input() notify: Subject<boolean>;

  ngOnInit(){
     this.notify.subscribe(v => { 
        console.log("I am from child");
     });
  }

}

//PARENT
export class ParentComp {

    notify: Subject<boolean> = new Subject();

    notifyChild(){
        this.notify.next(true);
    }

}
//子对象
@组成部分({
选择器:'子组件',
模板:“子项”
})
类子组件{
doSomething(){
console.log('我来自孩子')
}
}
//母公司
@组成部分({
选择器:“父组件”,
模板:“”,
})
类ParentComponent{
@ViewChild(ChildComponent)子级:ChildComponent;
ngAfterViewInit(){
这个。孩子。doSomething();
}
}
2nd(通知子组件调用某物):

// CHILD
@Component({
  selector: 'child-component',
  template: '<p>child</p>'
})

class ChildComponent {

  doSomething() {
    console.log('I am from child')
  }

}

// PARENT
@Component({
  selector: 'parent-component',
  template: '<child-component></child-component>',
})

class ParentComponent{

  @ViewChild(ChildComponent ) child: ChildComponent;

  ngAfterViewInit() {
    this.child.doSomething();
  }
}
//CHILD
export class ChildComponent implements OnInit {

  @Input() notify: Subject<boolean>;

  ngOnInit(){
     this.notify.subscribe(v => { 
        console.log("I am from child");
     });
  }

}

//PARENT
export class ParentComp {

    notify: Subject<boolean> = new Subject();

    notifyChild(){
        this.notify.next(true);
    }

}
//子对象
导出类ChildComponent实现OnInit{
@输入()通知:主题;
恩戈尼尼特(){
this.notify.subscribe(v=>{
console.log(“我来自儿童”);
});
}
}
//母公司
导出类ParentComp{
通知:主题=新主题();
notifyChild(){
this.notify.next(true);
}
}
我的问题是:

1) 第一种方法的利弊是什么?另外,如果您从父级调用子级的方法,这是否意味着您的组件的体系结构不好,或者需要修复其他问题

2) 第二种方法的利弊是什么

3) 避开它们好吗


我正在拼命地寻找这些问题的答案(有解释),如果有人能提供答案那就太好了。

如果可能的话,我会避免使用任何一种方法。如果你发现自己需要做很多这件事,那么你可能没有在父母和孩子之间正确地划分责任。您应该将所有必要的数据传递给子级,以便它知道何时调用任何函数,如果仍然不调用,则可能不是组件的责任。话虽如此,如果你发现自己正在编写一个相当复杂的应用程序,并且仍然需要大量的这个功能,我会使用类似ngrx的东西来正确管理状态。此外,如果要使用第二种方法,则应将主题分离为服务。至于推理,随着应用程序规模和复杂性的增长,依赖可预测的信息流和操作非常方便,这就是为什么ngrx可能有用,但在应用程序中多次使用第一种或第二种方法可能不会杀死你。

你可以使用changedetection:

// CHILD
@Component({
  selector: 'child-component',
  template: '<p>child</p>',
  changeDetection: ChangeDetectionStrategy.OnPush
})

class ChildComponent implements onChanges{
  @Input() status: boolean;
  doSomething() {
    console.log('I am from child')
  }

  ngOnChanges(changes: SimpleChanges) {
    if (changes.status) {
        this.doSomething();
    }
  }

}

// PARENT
@Component({
  selector: 'parent-component',
  template: '<child-component [status]="status"></child-component>',
})

class ParentComponent{

  status: boolean;

  ngAfterViewInit() {
    this.status = true;
  }
}
//子对象
@组成部分({
选择器:'子组件',
模板:“child

”, changeDetection:ChangeDetectionStrategy.OnPush }) 类ChildComponent实现onChanges{ @输入()状态:布尔; doSomething(){ console.log('我来自孩子') } ngOnChanges(更改:SimpleChanges){ 如果(更改状态){ 这个。doSomething(); } } } //母公司 @组成部分({ 选择器:“父组件”, 模板:“”, }) 类ParentComponent{ 状态:布尔型; ngAfterViewInit(){ this.status=true; } }
这两种实现都违背了关注点分离的原则。子组件不应该负责为父组件计算内容,因为这意味着没有子组件,父组件可能无法工作。
如果不同的组件需要一个函数或一些计算值,则可能应该将它们放在一个公共服务中,以便注入到两个组件中。

答案在很大程度上取决于您想要实现什么。在我的公司里,我们一般都尽量避开主题,但也尽量避开儿童。如果我们需要在它们之间进行选择,ViewChild将是我们的首选。无法真正解释,但主题更复杂,更难理解。我不认为1方法有任何问题,因为您正在调用child的方法。它类似于使用html按钮并调用它的click事件。我认为组件是用户添加的自定义标记,所以如果您在ts文件和调用方法中使用它们,就不会有什么问题。注意:这是我的观点,当存在父子关系时,我不会特别使用第二种方法,相反,我应该创建带有主题的服务并注入该服务以提供组件之间的通信,您可以参考angular.io站点,其中使用服务是提供组件之间通信的一种方式