1. Имеется общий компонент
MainComponent, чей шаблон выглядит следующим образом:
<!-- ===== [MAIN] ===== -->
<div class="main">
<!-- ========== [Общая шапка] ========== -->
<div *ngIf="headerVisibility">
<div class="header">
<h2 class="heading_text">{{ЗДЕСЬ_БЫ_ПОДСТАВЛЯЛСЯ_ЗАГОЛОВОК}}</h2>
<div class="header_buttons">
<button
*ngFor="let btn of МАССИВ_ВСЕХ_ДОСТУПНЫХ_КНОПОК_ПО_ТЕКУЩЕМУ_РОУТУ(editUser(), addUser())"
class="{{btn.НАЗВАНИЕ_КЛАССА_КНОПКИ}}"
(click)="btn.ФУНКЦИЯ_ИЗ_ВСТАВЛЯЕМОГО_ПО_РОУТУ_КОМПОНЕНТА()"
title="{{btn.НАЗВАНИЕ_КНОПКИ}}"
></button>
</div>
</div>
</div>
<!-- Вставляемый по роуту компонент -->
<router-outlet></router-outlet>
</div>
2. Сам код общего компонента
MainComponent:
import { Component, OnInit } from '@angular/core';
import { HeaderService } from '@app/shared/services/header.service';
@Component({
selector: 'app-main'
templateUrl: './main.component.html',
styleUrls: ['./main.component.less']
})
export class MainComponent implements OnInit {
title: string; // текущий заголовок хэдэра
headerVisibility: boolean; // текущее состояние отображения хэдэра
headerButtons = new Array<Object>(); // текущий набор кнопок хэдэра
constructor ( private headerService: HeaderService ) { }
ngOnInit() {
// подписываемся на объекты, чтобы отлавливать изменения
this.headerService.visibility.subscribe((newMode: boolean) => {this.headerVisibility = newMode});
this.headerService.title.subscribe((newTitle: string) => {this.title = newTitle});
this.headerButtons = this.headerService.getButtons(); // получаем массив кнопок
}
}
3. Код компонента
UsersComponent, который грузится по роуту '/users/'.
import { Component, OnInit } from '@angular/core';
import { HeaderService } from '@app/shared/services/header.service';
@Component({
selector: 'app-users',
templateUrl: './users.component.html',
styleUrls: ['./users.component.less']
})
export class UsersComponent implements OnInit {
constructor ( private headerService: HeaderService ) { }
ngOnInit() {
this.headerService.addButton(this.addUser.bind(this), 'add_button_class', 'MyButtonTItle');
}
editUser(id: number) {
console.log('EDITING_USER_HERE');
}
addUser() {
console.log('ADDING_USER_HERE');
}
}
В нем как раз есть функции
editUser,
addUser которые должны заполнить массив
headerButtons в компоненте
MainComponent и тем самым попасть в директиву
(click) в шаблон компонента
MainComponent
4. Мой вариант реализации сервиса:
import { Injectable } from '@angular/core';
import { BehaviorSubject } from 'rxjs';
@Injectable({
providedIn: 'root'
})
export class HeaderService
{
constructor(){}
visibility = new BehaviorSubject<Boolean>(true); // видимость header'a как такового
title = new BehaviorSubject<String>('Заголовок хэдэра по умолчанию'); // заголовок
buttons = new Array<Object>(); // кнопки
addButton(buttonFunc: Function, className: string, title: string) {
this.buttons.push({
buttonFunc,
className,
title
});
}
getButtons() { // чтобы получить массив объектов с информацией о кнопках
return this.buttons;
}
}