Как вызвать функцию из одного компонента в другом?

В Angular существует несколько способов вызова функции из одного компонента в другом:

1. Использование декоратора @Output:
В этом случае компонент A будет содержать функцию, которую нам нужно вызвать, а компонент B будет вызывать эту функцию. Для этого в компоненте A мы добавляем декоратор @Output перед объявлением функции, которую хотим вызвать. Затем мы используем событие EventEmitter, чтобы вызвать эту функцию и передать в нее данные из компонента B. В компоненте B мы обращаемся к событию, привязываемому к функции из компонента A, и вызываем его, передавая нужные данные.

Пример:
В компоненте A:

   import { Component, EventEmitter, Output } from '@angular/core';

   @Component({
     ...
   })
   export class ComponentA {
     @Output() functionToCall: EventEmitter<any> = new EventEmitter<any>();

     callFunction(data: any) {
       // Вызываем функцию и передаем данные
       this.functionToCall.emit(data);
     }
   }

В компоненте B:

   import { Component } from '@angular/core';

   @Component({
     ...
   })
   export class ComponentB {
     callFunctionFromA(data: any) {
       // Вызываем функцию из компонента A
       console.log('Вызвана функция из компонента A с данными:', data);
     }
   }

В шаблоне компонента B:

   <app-component-a (functionToCall)="callFunctionFromA($event)"></app-component-a>

2. Использование сервисов:
Мы можем создать сервис, который будет содержать нужную функцию, и затем внедрить его в компоненты, которые должны вызывать эту функцию. Таким образом, функция станет доступной для вызова в любом месте, где сервис был внедрен.

Пример:
Создаем сервис:

   import { Injectable } from '@angular/core';

   @Injectable()
   export class MyService {
     callFunction(data: any) {
       console.log('Вызвана функция из сервиса с данными:', data);
     }
   }

В компоненте A внедряем сервис и вызываем его функцию:

   import { Component } from '@angular/core';
   import { MyService } from './my.service';

   @Component({
     ...
   })
   export class ComponentA {
     constructor(private myService: MyService) { }

     callFunction(data: any) {
       this.myService.callFunction(data);
     }
   }

В компоненте B также внедряем сервис и вызываем его функцию:

   import { Component } from '@angular/core';
   import { MyService } from './my.service';

   @Component({
     ...
   })
   export class ComponentB {
     constructor(private myService: MyService) { }

     callFunctionFromA(data: any) {
       this.myService.callFunction(data);
     }
   }

3. Использование @ViewChild:
Если функция, которую мы хотим вызвать, находится в одном компоненте, а мы хотим вызвать ее из другого компонента, мы можем использовать @ViewChild. С помощью @ViewChild мы можем получить доступ к определенному компоненту и вызвать его функцию, используя этот экземпляр компонента.

Пример:
В компоненте A:

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

   @Component({
     ...
   })
   export class ComponentA {
     callFunction() {
       console.log('Вызвана функция из компонента A');
     }
   }

В компоненте B мы используем @ViewChild для получения доступа к компоненту A и вызываем его функцию:

   import { Component, AfterViewInit, ViewChild } from '@angular/core';
   import { ComponentA } from './component-a.component';

   @Component({
     ...
   })
   export class ComponentB implements AfterViewInit {
     @ViewChild(ComponentA) componentA: ComponentA;

     ngAfterViewInit() {
       this.componentA.callFunction();
     }
   }