Tidak ada yang setara dengan $scope.emit()
atau$scope.broadcast()
dari AngularJS. EventEmitter di dalam komponen sudah dekat, tetapi seperti yang Anda sebutkan, itu hanya akan memancarkan sebuah peristiwa ke komponen induk langsung.
Di Angular, ada alternatif lain yang akan saya coba jelaskan di bawah ini.
@Input () binding memungkinkan model aplikasi untuk dihubungkan dalam grafik objek yang diarahkan (root to leaves). Perilaku default dari strategi detektor perubahan komponen adalah untuk menyebarkan semua perubahan ke model aplikasi untuk semua ikatan dari komponen yang terhubung.
Selain: Ada dua jenis model: Lihat Model dan Model Aplikasi. Model aplikasi terhubung melalui @Input () binding. Model tampilan hanyalah properti komponen (tidak didekorasi dengan @Input ()) yang terikat dalam templat komponen.
Untuk menjawab pertanyaan Anda:
Bagaimana jika saya perlu berkomunikasi antara komponen saudara?
Model Aplikasi Bersama : Saudara dapat berkomunikasi melalui model aplikasi bersama (seperti sudut 1). Misalnya, ketika satu saudara kandung membuat perubahan ke model, saudara kandung lainnya yang memiliki ikatan dengan model yang sama diperbarui secara otomatis.
Component Events : Komponen child dapat memancarkan sebuah event ke komponen induk menggunakan binding @Output (). Komponen induk dapat menangani acara, dan memanipulasi model aplikasi atau model tampilan itu sendiri. Perubahan pada Model Aplikasi secara otomatis disebarkan ke semua komponen yang secara langsung atau tidak langsung mengikat ke model yang sama.
Acara Layanan : Komponen dapat berlangganan acara layanan. Misalnya, dua komponen saudara dapat berlangganan ke acara layanan yang sama dan merespons dengan memodifikasi model masing-masing. Lebih lanjut tentang ini di bawah ini.
Bagaimana saya bisa berkomunikasi antara komponen Root dan komponen yang bersarang dalam beberapa level?
- Model Aplikasi Bersama: Model aplikasi dapat diturunkan dari komponen Root ke sub-komponen bersarang melalui @Input () binding. Perubahan model dari komponen apa pun akan secara otomatis menyebar ke semua komponen yang memiliki model yang sama.
- Acara Layanan : Anda juga dapat memindahkan EventEmitter ke layanan bersama, yang memungkinkan komponen mana pun untuk menyuntikkan layanan dan berlangganan ke acara tersebut. Dengan begitu, komponen Root dapat memanggil metode layanan (biasanya bermutasi model), yang pada gilirannya memancarkan suatu peristiwa. Beberapa lapisan ke bawah, komponen cucu yang juga menyuntikkan layanan dan berlangganan ke acara yang sama, dapat menanganinya. Pengatur kejadian apa pun yang mengubah Model Aplikasi yang dibagikan, akan secara otomatis menyebar ke semua komponen yang bergantung padanya. Ini mungkin setara dengan terdekat
$scope.broadcast()
dari Angular 1. Bagian selanjutnya menjelaskan ide ini secara lebih rinci.
Contoh Layanan yang Dapat Diobservasi yang menggunakan Acara Layanan untuk Menyebarkan Perubahan
Berikut adalah contoh layanan yang dapat diamati yang menggunakan acara layanan untuk menyebarkan perubahan. Ketika TodoItem ditambahkan, layanan memancarkan acara yang memberitahukan pelanggan komponennya.
export class TodoItem {
constructor(public name: string, public done: boolean) {
}
}
export class TodoService {
public itemAdded$: EventEmitter<TodoItem>;
private todoList: TodoItem[] = [];
constructor() {
this.itemAdded$ = new EventEmitter();
}
public list(): TodoItem[] {
return this.todoList;
}
public add(item: TodoItem): void {
this.todoList.push(item);
this.itemAdded$.emit(item);
}
}
Berikut adalah bagaimana komponen root akan berlangganan acara:
export class RootComponent {
private addedItem: TodoItem;
constructor(todoService: TodoService) {
todoService.itemAdded$.subscribe(item => this.onItemAdded(item));
}
private onItemAdded(item: TodoItem): void {
// do something with added item
this.addedItem = item;
}
}
Komponen anak yang bersarang beberapa level akan berlangganan acara dengan cara yang sama:
export class GrandChildComponent {
private addedItem: TodoItem;
constructor(todoService: TodoService) {
todoService.itemAdded$.subscribe(item => this.onItemAdded(item));
}
private onItemAdded(item: TodoItem): void {
// do something with added item
this.addedItem = item;
}
}
Berikut adalah komponen yang memanggil layanan untuk memicu acara (itu bisa berada di mana saja di pohon komponen):
@Component({
selector: 'todo-list',
template: `
<ul>
<li *ngFor="#item of model"> {{ item.name }}
</li>
</ul>
<br />
Add Item <input type="text" #txt /> <button (click)="add(txt.value); txt.value='';">Add</button>
`
})
export class TriggeringComponent{
private model: TodoItem[];
constructor(private todoService: TodoService) {
this.model = todoService.list();
}
add(value: string) {
this.todoService.add(new TodoItem(value, false));
}
}
Referensi: Ubah Deteksi dalam Angular