繁体   English   中英

Angular 11 - 从孩子调用父函数

[英]Angular 11 - Call parent function from child

我已经多次正确使用了Angular组件之间的值传递(输入/输出),但我发现了以下特殊情况,我找不到解决方案:

我有两个组件:

  1. home.component(父组件)

父组件又包含另一个从外部库获得的选项卡之间的导航组件,该组件在选项卡中加载子组件:“task.component”:

.html 文件:

<div>
<app-tabs [tabs]="tabs" [activeTab]="activeTab" (id)="onId($event)"></app-tabs>
</div>

ts文件:

onId($event) {
    // $event would contain the id obtained in the child component
}
  1. tasks.component(子组件)

子组件包含从按钮调用父组件的调用:

.html 文件:

<button type="button" (click)="play('task/play', 30)">Play</button>

ts文件:

@Output() id= new EventEmitter<number>();
play(url: string, id: number) {
this.tasksService.playTask(url).subscribe(
  response => {
    // From here, I need to communicate with the parent and access a method that is in the parent.
    // this.id.emit(id);
  },
  err => {
  }
);
}

在其他情况下,我将参数从子级传递给父级没有问题,因为我使用自己的组件,但是当使用中间选项卡组件时,我没有得到它。 (必须使用选项卡组件)。 我认为它不起作用是合乎逻辑的,因为“输出”必须直接传递给组件“task.component”。 也就是说,我无法将“输出”“id”传递给“app-tabs”组件。

我怎么能做到?

子组件(或孙子组件)似乎包含在子路由中。

在这种情况下,一种解决方案可能是使用共享服务将通知从子组件发送到父组件。 (或应用程序内的任何其他组件)。

为此,我们需要一个可注入服务(或集成到现有服务中):

notification.service.ts中:

@Injectable()
export class NotificationService {
  _taskPlayed$ = new Subject<number>();

  get taskPlayed$() {
    return this._taskPlayed$.asObservable();
  }

  taskPlayed(id: number) {
    this._taskPlayed$.next(id);
  }
}

请务必在模块提供程序中添加此服务。

然后,我们可以在子(或任何组件)中注入服务,并调用taskPlayed方法以在 observable 中发出新的值/事件。

所以,在child.component.ts

export class ChildComponent {
  constructor(private notificationService: NotificationService) {}

  playTask() {
    this.notificationService.taskPlayed(1);
  }
}

同样,我们在父级(或应用程序中的任何组件)中注入服务,并从服务订阅taskPlayed$ observable。 (一定要在组件被销毁时取消订阅)。

所以,在parent.component.ts

export class ParentComponent implements OnInit, OnDestroy {
  subscription!: Subscription;

  constructor(private notificationService: NotificationService) {}

  ngOnInit(): void {
    this.subscription = this.notificationService.taskPlayed$.subscribe((id) => {
      // do something with id...
      ....
    });
  }

  ngOnDestroy(): void {
    this.subscription?.unsubscribe();
  }
}

在这个例子中,只有id值是通过Observable发送的,但我们也可以传递一个更复杂的对象。

export class NotificationService {
  _taskPlayed$ = new Subject<{ id: number, title: string }>();

  get taskPlayed$() {
    return this._taskPlayed$.asObservable();
  }

  taskPlayed(task: {id: number, title: string}) {
    this._taskPlayed$.next(task);
  }
}

暂无
暂无

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

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